QT之QByteArry
Qt通过QByteArray为我们提供了一个字节数组容器。QByteArray既可以用来存储原始的字节,包括'\0',也可以用来存储传统的8-bit 的以'\0'结尾的字符串。使用QByteArray比使用普通的const char* 更方便。并且,在底层,它可以确保其中存储的数据以'\0'结尾,并且通过隐式共享(写时拷贝)策略减少内存的使用和不必要的数据复制。
1、QByteArry的初始化
QByteArray ba;
ba.resize(3);
ba[0] = 0x30;
ba[1] = 0x31;
ba[2] = 0x32;
QByteArray strInt("1234");
2、QByteArry的访问
- 1、访问方式共有四种:[]、data[]和at()、 constData[];
- 2、[]和data[]为可读可写;
- 3、at()和constData[]仅为可读。如果仅是读,则通过at()和constData[]访问速度最快。
QByteArray ba;
ba.resize(6);
ba[0] = 0x3c;
ba[1] = 0xb8;
ba[2] = 0x64;
ba[3] = 0x18;
ba[4] = 0xca;
ba.data()[5] = 0x31; //可读可写访问
//可读可写访问
qDebug()<<"[]"<<ba[2];
qDebug()<<"data()"<<ba.data()[2];
//仅读访问
qDebug()<<"at()"<<ba.at(2);
qDebug()<<"constData()"<<ba.constData()[2];
3、QByteArry的字节大小
QByteArray可以嵌入“\0” 字节,size()函数总是返回整个数组的大小,包括嵌入的’\ 0’字节,但不包括QByteArray自动添加的终止’\ 0’.
QByteArray s;
s.resize(5);
s[0] = '1';
s[1] = '2';
s[2] = '3';
s[3] = '\0';
s[4] = 'a';
cout << s.size() << endl; //打印大小5,但实际在内存中存储的大小为6,因为自动加了/0的特点
cout << s << endl; //屏幕打印的是:“123 a”
//s.size()为5,但是字节数组在最后还会保留一个额外的’\ 0’字符, 以便如果使用一个函数来请求指向底层数据的指针(例如调用data()),那么指出的数据保证被’\ 0’终止。
4、QByteArry的相互转换
5.1 Hex转换(1个hex编码由两个字符构成)
//把Hex编码转换为char存储到QByteArray:
QByteArray text = QByteArray::fromHex("517420697320677265617421");
text.data(); // returns "Qt is great!"
//"517420697320677265617421" 每两个字符表示一个16进制编码,如51表示"Q"
//把QByteArray转为Hex编码:
QByteArray ba;
ba.resize(3);
ba[0] = 0x1;
ba[1] = 0x2;
ba[2] = 0x3;
qDebug() << ba.toHex(); //return "010203"
5.2 数值转换与输出
//尽管QByteArray是一个集合,但也可以作为一个特殊形式的数值用,其灵活的转换格式,可大大方便各种格式数据转换与显示的需求。如显示二进制和十六进制、显示科学计数和指定小数位的数值。
int n = 63;
qDebug()<<QByteArray::number(n); // returns "63"
qDebug()<<QByteArray::number(n, 16); // returns "3f"
qDebug()<<QByteArray::number(n, 16).toUpper(); // returns "3F"
qDebug()<<QByteArray::number(n, 2); // returns "111111"
qDebug()<<QByteArray::number(n, 8); // returns "77"
//按照指定进制格式直接赋值,其中n可以是各类常见数值类型:
QByteArray ba;
int n = 63;
ba.setNum(n); // ba == "63"
ba.setNum(n, 16); // ba == "3f"
//把数值按指定格式和小数位转换输出,小数位四舍五入:
QByteArray ba1 = QByteArray::number(12.3456, 'E', 3);
QByteArray ba2 = QByteArray::number(12.3456, 'f', 3);
qDebug()<<ba1; // returns "1.235E+01"
qDebug()<<ba2; // returns "12.346"
5.3 QByteArray字符串数值转为各类数值
QByteArray若为数值,可通过to**方法转为各种类型数据,示例如下:
QByteArray strInt("1234");
bool ok0;
qDebug() << strInt.toInt(); // return 1234
qDebug() << strInt.toInt(&ok0,16); // return 4660, 默认把1234作为0x1234,对应十进制数值为4660
QByteArray string("1234.56");
bool ok1;
qDebug() << string.toInt(); // return 0, 小数均视为0
qDebug() << string.toInt(&ok1,16); // return 0, 小数均视为0
qDebug() << string.toFloat(); // return 1234.56
qDebug() << string.toDouble(); // return 1234.56
QByteArray str("FF");
bool ok2;
qDebug() << str.toInt(&ok2, 16); // return 255, ok2 == true
qDebug() << str.toInt(&ok2, 10); // return 0, ok == false, 转为十进制失败
5.4 大小写转换
QByteArray若为带大小写的字符串,可通过toUpper()和toLower()方法实现大小写转换:
QByteArray x("Qt by THE QT COMPANY");
QByteArray y = x.toLower(); // y == "qt by the qt company"
QByteArray z = x.toUpper(); // z == "QT BY THE QT COMPANY
3、QByteArry的接口函数
(1). char *QByteArray::data()
//返回指向字节数组中存储的数据的指针。该指针可用于访问和修改组成数组的字节。具体访问字节数组中的某一个,采用ba.data()[0]–>访问第0个
QByteArray ba("Hello world");
char *data = ba.data();//返回一个指向字节数组ba的数据指针,指向第一个字符
qDebug() << ba.data();//打印整个字符
while (*data)
{
cout << "[" << *data << "]" << endl;
++data;
}
//得到结果 [ H ] ,[ e ] ,[ l ] ,[ l ] ,[ o ], [ ], [ w ] ,[ r ] ,[ l ] ,[ d ].
(2). QByteArray &QByteArray::fill(char ch, int size = -1)
//将字节数组中的每个字节设置为字符ch。如果size与-1(默认值)不同,则字节数组将预先调整为大小。
QByteArray ba("Istambul");
ba.fill('o');
// ba == "oooooooo"
ba.fill('X', 2);
// ba == "XX"
(3). int QByteArray::indexOf(const QByteArray &ba, int from = 0) const
//返回该字节数组中第一次出现字节数组ba的索引位置,从索引位置向前搜索。如果找不到ba,则返回-1 。
QByteArray x("sticky question");
QByteArray y("sti");
x.indexOf(y); // returns 0
x.indexOf(y, 1); // returns 10
x.indexOf(y, 10); // returns 10
x.indexOf(y, 11); // returns -1
(4). bool QByteArray::isEmpty() const
如果字节数组的大小为0,返回true; 否则返回false。
(5). QByteArray QByteArray::left(int len) const
//返回一个包含该字节数组最左侧len个字节的字节数组,如果len大于size(),则返回整个字节数组.
QByteArray x("Pineapple");
QByteArray y = x.left(4); // y == "Pine"
(6). QByteArray QByteArray::number(int n, int base = 10)
//返回一个字节数组,其中包含等价于数字n到基数的字符串(默认为10)。基数可以是2到36之间的任何值。
int n = 63;
QByteArray::number(n); // returns "63"
QByteArray::number(n, 16); // returns "3f"
QByteArray::number(n, 16).toUpper(); // returns "3F"
//可以理解为 int 类型到QByteArray类型的转化。
(7). QByteArray &QByteArray::setNum(int n, int base = 10)
//将字节数组设置为基数为n的打印值(默认为10)并返回对字节数组的引用。基数可以是介于2和36之间的任何值。对于非10以外的其他值,n被视为无符号整数。
QByteArray ba;
int n = 63;
ba.setNum(n); // ba == "63"
ba.setNum(n, 16); // ba == "3f"
(8). int QByteArray::size() const
//返回此字节数组中的字节数。
QByteArray ba("Hello");
int n = ba.size(); // n == 5
ba.data()[0]; // returns 'H' 操作某一位的方法
ba.data()[4]; // returns 'o'
ba.data()[5]; // returns '\0'
(9)double QByteArray::toDouble(bool *ok = Q_NULLPTR) const
float QByteArray::toFloat(bool *ok = Q_NULLPTR) const
int QByteArray::toInt(bool *ok = Q_NULLPTR, int base = 10) const
//返回转换为double值的字节数组。
QByteArray string("1234.56");
double a = string.toDouble(); // a == 1234.56
(10). QByteArray QByteArray::toHex() const
返回字节数组的十六进制编码副本。十六进制编码使用数字 0 - 9 和字母 a - f。
See also fromHex().