📄 qcstring.cpp
字号:
/************************************************************************ Copyright (C) 2000-2005 Trolltech AS. All rights reserved.**** This file is part of the Qtopia Environment.** ** This program is free software; you can redistribute it and/or modify it** under the terms of the GNU General Public License as published by the** Free Software Foundation; either version 2 of the License, or (at your** option) any later version.** ** A copy of the GNU GPL license version 2 is included in this package as ** LICENSE.GPL.**** This program is distributed in the hope that it will be useful, but** WITHOUT ANY WARRANTY; without even the implied warranty of** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. ** See the GNU General Public License for more details.**** In addition, as a special exception Trolltech gives permission to link** the code of this program with Qtopia applications copyrighted, developed** and distributed by Trolltech under the terms of the Qtopia Personal Use** License Agreement. You must comply with the GNU General Public License** in all respects for all of the code used other than the applications** licensed under the Qtopia Personal Use License Agreement. If you modify** this file, you may extend this exception to your version of the file,** but you are not obligated to do so. If you do not wish to do so, delete** this exception statement from your version.** ** See http://www.trolltech.com/gpl/ for GPL licensing information.**** Contact info@trolltech.com if any conditions of this licensing are** not clear to you.************************************************************************/#include "qstring.h"#include "qregexp.h"#include "qdatastream.h"#ifdef QT_THREAD_SUPPORT# include <private/qmutexpool_p.h>#endif // QT_THREAD_SUPPORT#include <stdio.h>#include <stdarg.h>#include <stdlib.h>#include <ctype.h>#include <limits.h>#ifndef QT_NO_COMPRESS#include "../3rdparty/zlib/zlib.h"#endif/***************************************************************************** Safe and portable C string functions; extensions to standard string.h *****************************************************************************//*! \relates QCString This function is normally part of the C library. Qt implements memmove() for platforms that do not provide it. memmove() copies \a len bytes from \a src into \a dst. The data is copied correctly even if \a src and \a dst overlap.*/void *qmemmove( void *dst, const void *src, uint len ){ register char *d; register char *s; if ( dst > src ) { d = (char *)dst + len - 1; s = (char *)src + len - 1; while ( len-- ) *d-- = *s--; } else if ( dst < src ) { d = (char *)dst; s = (char *)src; while ( len-- ) *d++ = *s++; } return dst;}/*! \relates QCString Returns a duplicate string. Allocates space for a copy of \a src, copies it, and returns a pointer to the copy. If \a src is 0, it immediately returns 0. The returned string must be deleted using \c delete[].*/char *qstrdup( const char *src ){ if ( !src ) return 0; char *dst = new char[strlen(src)+1]; Q_CHECK_PTR( dst ); return strcpy( dst, src );}/*! \fn char *qstrcpy( char *dst, const char *src ) \relates QCString A safe strcpy() function. Copies all characters up to and including the '\0' from \a src into \a dst and returns a pointer to \a dst.*//*! \relates QCString A safe strncpy() function. Copies at most \a len bytes from \a src (stopping at \a len or the terminating '\0' whichever comes first) into \a dst and returns a pointer to \a dst. Guarantees that \a dst is '\0'-terminated. If \a src or \a dst is 0, returns 0 immediately. \sa qstrcpy()*/char *qstrncpy( char *dst, const char *src, uint len ){ if ( !src || !dst ) return 0; strncpy( dst, src, len ); if ( len > 0 ) dst[len-1] = '\0'; return dst;}/*! \fn uint qstrlen( const char *str ); \relates QCString A safe strlen function. Returns the number of characters that precede the terminating '\0'. or 0 if \a str is 0.*//*! \fn int qstrcmp( const char *str1, const char *str2 ); \relates QCString A safe strcmp() function. Compares \a str1 and \a str2. Returns a negative value if \a str1 is less than \a str2, 0 if \a str1 is equal to \a str2 or a positive value if \a str1 is greater than \a str2. Special case I: Returns 0 if \a str1 and \a str2 are both 0. Special case II: Returns a random nonzero value if \a str1 is 0 or \a str2 is 0 (but not both). \sa qstrncmp() qstricmp() qstrnicmp() \link #asciinotion Note on character comparisons \endlink*//*! \fn int qstrncmp( const char *str1, const char *str2, uint len ); \relates QCString A safe strncmp() function. Compares at most \a len bytes of \a str1 and \a str2. Returns a negative value if \a str1 is less than \a str2, 0 if \a str1 is equal to \a str2 or a positive value if \a str1 is greater than \a str2. Special case I: Returns 0 if \a str1 and \a str2 are both 0. Special case II: Returns a random nonzero value if \a str1 is 0 or \a str2 is 0 (but not both). \sa qstrcmp(), qstricmp(), qstrnicmp() \link #asciinotion Note on character comparisons \endlink*//*! \relates QCString A safe stricmp() function. Compares \a str1 and \a str2 ignoring the case. Returns a negative value if \a str1 is less than \a str2, 0 if \a str1 is equal to \a str2 or a positive value if \a str1 is greater than \a str2. Special case I: Returns 0 if \a str1 and \a str2 are both 0. Special case II: Returns a random nonzero value if \a str1 is 0 or \a str2 is 0 (but not both). \sa qstrcmp(), qstrncmp(), qstrnicmp() \link #asciinotion Note on character comparisons \endlink*/int qstricmp( const char *str1, const char *str2 ){ register const uchar *s1 = (const uchar *)str1; register const uchar *s2 = (const uchar *)str2; int res; uchar c; if ( !s1 || !s2 ) return s1 ? 1 : ( s2 ? -1 : 0 ); for ( ; !(res = (c=tolower(*s1)) - tolower(*s2)); s1++, s2++ ) if ( !c ) // strings are equal break; return res;}/*! \relates QCString A safe strnicmp() function. Compares at most \a len bytes of \a str1 and \a str2 ignoring the case. Returns a negative value if \a str1 is less than \a str2, 0 if \a str1 is equal to \a str2 or a positive value if \a str1 is greater than \a str2. Special case I: Returns 0 if \a str1 and \a str2 are both 0. Special case II: Returns a random nonzero value if \a str1 is 0 or \a str2 is 0 (but not both). \sa qstrcmp(), qstrncmp() qstricmp() \link #asciinotion Note on character comparisons \endlink*/int qstrnicmp( const char *str1, const char *str2, uint len ){ register const uchar *s1 = (const uchar *)str1; register const uchar *s2 = (const uchar *)str2; int res; uchar c; if ( !s1 || !s2 ) return s1 ? 1 : ( s2 ? -1 : 0 ); for ( ; len--; s1++, s2++ ) { if ( (res = (c=tolower(*s1)) - tolower(*s2)) ) return res; if ( !c ) // strings are equal break; } return 0;}static Q_UINT16 crc_tbl[16];static bool crc_tbl_init = FALSE;static void createCRC16Table() // build CRC16 lookup table{ register uint i; register uint j; uint v0, v1, v2, v3; for ( i = 0; i < 16; i++ ) { v0 = i & 1; v1 = ( i >> 1 ) & 1; v2 = ( i >> 2 ) & 1; v3 = ( i >> 3 ) & 1; j = 0;#undef SET_BIT#define SET_BIT(x, b, v) (x) |= (v) << (b) SET_BIT( j, 0, v0 ); SET_BIT( j, 7, v0 ); SET_BIT( j, 12, v0 ); SET_BIT( j, 1, v1 ); SET_BIT( j, 8, v1 ); SET_BIT( j, 13, v1 ); SET_BIT( j, 2, v2 ); SET_BIT( j, 9, v2 ); SET_BIT( j, 14, v2 ); SET_BIT( j, 3, v3 ); SET_BIT( j, 10, v3 ); SET_BIT( j, 15, v3 ); crc_tbl[i] = j; }}/*! \relates QMemArray Returns the CRC-16 checksum of \a len bytes starting at \a data. The checksum is independent of the byte order (endianness).*/Q_UINT16 qChecksum( const char *data, uint len ){ if ( !crc_tbl_init ) { // create lookup table#ifdef QT_THREAD_SUPPORT QMutexLocker locker( qt_global_mutexpool ? qt_global_mutexpool->get( &crc_tbl_init ) : 0 );#endif // QT_THREAD_SUPPORT if ( !crc_tbl_init ) { createCRC16Table(); crc_tbl_init = TRUE; } } register Q_UINT16 crc = 0xffff; uchar c; uchar *p = (uchar *)data; while ( len-- ) { c = *p++; crc = ( (crc >> 4) & 0x0fff ) ^ crc_tbl[((crc ^ c) & 15)]; c >>= 4; crc = ( (crc >> 4) & 0x0fff ) ^ crc_tbl[((crc ^ c) & 15)]; } return ~crc & 0xffff;}/*! \fn QByteArray qCompress( const QByteArray& data ) \relates QByteArray Compresses the array \a data and returns the compressed byte array using zlib. \sa qUncompress()*//*! \relates QByteArray \overload Compresses the array \a data which is \a nbytes long and returns the compressed byte array.*/#ifndef QT_NO_COMPRESSQByteArray qCompress( const uchar* data, int nbytes ){ if ( nbytes == 0 ) { QByteArray tmp( 4 ); tmp.fill( 0 ); return tmp; } if ( !data ) {#if defined(QT_CHECK_RANGE) qWarning( "qCompress: data is NULL." );#endif return QByteArray(); } ulong len = nbytes * 2; QByteArray bazip; int res; do { bazip.resize( len + 4 ); res = ::compress( (uchar*)bazip.data()+4, &len, (uchar*)data, nbytes ); switch ( res ) { case Z_OK: bazip.resize( len + 4 ); bazip[0] = ( nbytes & 0xff000000 ) >> 24; bazip[1] = ( nbytes & 0x00ff0000 ) >> 16; bazip[2] = ( nbytes & 0x0000ff00 ) >> 8; bazip[3] = ( nbytes & 0x000000ff ); break; case Z_MEM_ERROR:#if defined(QT_CHECK_RANGE) qWarning( "qCompress: Z_MEM_ERROR: Not enough memory." );#endif bazip.resize( 0 ); break; case Z_BUF_ERROR: len *= 2; break; } } while ( res == Z_BUF_ERROR ); return bazip;}#endif/*! \fn QByteArray qUncompress( const QByteArray& data ) \relates QByteArray Uncompresses the array \a data and returns the uncompressed byte array. Returns an empty QByteArray if the input data was corrupt. \omit ADD THE FOLLOWING FOR Qt 4.0 This function will uncompress data compressed with qCompress() from this and any earlier Qt version, back to Qt 3.1 when this feature was added. \endomit \sa qCompress()*//*! \relates QByteArray \overload Uncompresses the array \a data which is \a nbytes long and returns the uncompressed byte array.*/#ifndef QT_NO_COMPRESSQByteArray qUncompress( const uchar* data, int nbytes ){ if ( !data ) {#if defined(QT_CHECK_RANGE) qWarning( "qUncompress: data is NULL." );#endif return QByteArray(); } if ( nbytes <= 4 ) {#if defined(QT_CHECK_RANGE) if ( nbytes < 4 || ( data[0]!=0 || data[1]!=0 || data[2]!=0 || data[3]!=0 ) ) qWarning( "qUncompress: Input data is corrupted." );#endif return QByteArray(); } ulong expectedSize = ( data[0] << 24 ) | ( data[1] << 16 ) | ( data[2] << 8 ) | data[3]; ulong len = QMAX( expectedSize, 1 ); QByteArray baunzip; int res; do { baunzip.resize( len ); res = ::uncompress( (uchar*)baunzip.data(), &len, (uchar*)data+4, nbytes-4 ); switch ( res ) { case Z_OK: if ( len != baunzip.size() ) baunzip.resize( len ); break; case Z_MEM_ERROR:#if defined(QT_CHECK_RANGE) qWarning( "qUncompress: Z_MEM_ERROR: Not enough memory." );#endif break; case Z_BUF_ERROR: len *= 2; break; case Z_DATA_ERROR:#if defined(QT_CHECK_RANGE) qWarning( "qUncompress: Z_DATA_ERROR: Input data is corrupted." );#endif break; } } while ( res == Z_BUF_ERROR ); if ( res != Z_OK ) baunzip = QByteArray(); return baunzip;}#endif/***************************************************************************** QByteArray documentation *****************************************************************************//*! \class QByteArray \reentrant \brief The QByteArray class provides an array of bytes. \ingroup collection \ingroup tools The QByteArray class provides an explicitly shared array of bytes. It is useful for manipulating memory areas with custom data. QByteArray is implemented as a QMemArray\<char\>. See the \l QMemArray documentation for further information.*//*! \fn QByteArray::QByteArray() Constructs an empty QByteArray.*//*! \fn QByteArray::QByteArray( int size ) Constructs a QByteArray of size \a size.*/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -