Qt数据结构详解

常用数据类型

qint8 quint8 qint16 quint16 qint32 quint32 qint64 quint64 qreal …

  • 文档索引
类型说明大小
qint8signed char1
quint8unsigned char1
qint16signed short2
quint16unsigned short2
qint32signed int4
quint32unsigned int4
qint64long long int8
quint64unsigned long long int8
qrealdouble8
  • 求绝对值: T qAbs(const T &t)
qreal absoluteVale;
qreal myValue = -5.78;
absoluteValue = qAbs(myValue);
  • 最大值与最小值

T &qMax(const T &value1, const T &value2)
T &qMin(const T &value1, const T &value2)

 int myValue - 6;
 int yourValue = 4;
 int minValue = qMin(myValue,yourValue);
  • 取中间值

const T &qBound(const T &min, const T &value, const T &max)

qint32 v_1 = 10;
qint32 v_2 = 20;
qint32 v_3 = 30;
qin32 boundeValue = qBound(v_1,v_2,v_3);
// boundedValue == 20
  • 比较浮点数大小

bool qFuzzyCompare(float p1, float p2)
bool qFuzzyCompare(double p1, double p2)

  • 随机数种子

void qsrand(uint seed);
Thread-safe version of the standard C++ srand() function

  • 生成随机数

int qrand();

  • 获取环境变量
QByteArray env = qgetenv("Path");
std::cout<< env.consData();
qDebug() << QString::fromLocal8Bit(env);

QSize QSizeF

QSize(int width, int height)
QSizeF(qreal width, qreal height)

QSize size(100,10);
size.rheight() += 5;
// result:(100,15)
QSize size(100,10);
size.reidth() += 20;
// result:(120,10)
QSize s(3,7);
QSize r(-1,4);
s -=r;
// result :(4,3)

QPoint QPointF

QPoint(int xpos, int ypos);
QPointF(qreal xpos, qreal ypos);

QPoint p(1, 2);
p.rx()--; 
// result:(0,2)
QPoint p(1, 2);
p.ry()++; 
// result:(1,3)
QPoint p(-1, 4);
p *= 2.5; 
// result:(-2,10)
QPoint p( 3, 7);
QPoint q(-1, 4);
p += q; 
// result :(2,11)

QRect

QRect(const QPoint &topLeft, const QPoint &bottomRight)
QRect(const QPoint &topLeft, const QSize &size)
QRect(int x, int y, int width, int height)

QRect r1(100, 200, 11, 16);
QRect r2(QPoint(100, 200), QSize(11, 16));

QString: Qt字符串操作

QString类提供了一个Unicode字符字符串。
QString(const QChar unicode, int size = -1)
QString(QChar ch)
QString(int size, QChar ch)
QString(QLatin1String str)
QString(const QString &other)
QString(QString &&other)
QString(const char str)
QString(const QByteArray &ba)

初始化
QString str = "OO";
// QString 使用 fromUtf8() 函数将 const char * 数据转换为 Unicode
追加
QString str = "IO";
str.prepend("this "); // 从前面追加
str.append("pram"); // 尾椎
// 也可以使用push_back、push_front
替换
QString x = "S";
QString y = "VC";
x.replace(0,0,y);
删除
// 按位删除
QString s = "Funck";
s.remove(1,3);

// 删除特定字符
QString t = "Ali Baba";
t.remove(QChar('a'),Qt::CaseInsensitive); // 不区分大小写

QString x = "Ali Baba";
x.remove(QChar('a'));  //Qt::CaseSensitive (default)区分大小写

QString str = "do you what to see!";
str.remove("11");

QString 插入
QString str = "fuck A";
str.insert(5, "BC");
判断为Empty | Null
QString.isEmpty();       // true
QString("").isEmpty();   // true
QString("X").isEmpty();  // false
QString("abc").isEmpty();// false

QString().isNull();     // true
QString("").isNull();   // false
QString("acb").isNull();//false
查找字符串出现的位置

int QString::indexOf(const QString &str, int from = 0, Qt::CaseSensitivity cs = Qt::CaseSensitive)const
返回第一次搜索到指定字符串的位置,从from开始搜索。

QString x = "stl emistl";
QString y = "stl";
x.indexOf(y); 		// 0:找到了第一个stl
x.indexOf(y,1);		// 7:找到了第二个stl
x.indexOf(y,7);		
x.indexOf(y,8);		// -1:没有找到对应的子串
查找字符串出现的次数
QString x = "A Sticky Question";
QString y   "sti";
x.count(y,Qt::CaseInsensitive); // 返回2 不区分大小写
x.count(y);						// 返回1
查找是否包含另一字符串
QString x = "Peter Pan";
x.contains("Peter",Qt::CaseInsensitive);// true(不区分大小写)
x.contains("peter");//false(默认区分大小写)
字符串截取
  • 向左截取
QString x = "coding is fun";
QString y = x.left(6); // y == "coding"
  • 向右截取
QString x = "coding is fun";
QString y = x.right(6); // y == "is fun" 
  • mid截取
QString x = "coding is fun";
QString y = x.mid(5, 4); // y == "g is" 从index=5开始截取,截取4个
QString z = x.mid(5); // z == "g is fun" 从index=5开始截取,截取到末尾
数字转QString

静态方法::[static] QString QString::number(uint n, int base = 10)

  • 默认十进制
qint32 num = 65534;
QString str = QString::number(num);
  • 十六进制
qint32 num = 65534;
QString str = QString::number(num,16); // fffe
  • 大写十六进制
qint32 num = 65534;
QString str = QString::number(num); // fffe
  • 浮点数
// 默认情况 6位
qreal num = 3.141592658;
QString str = String::num(num);// 3.14159

// 如果对精度有要求
qreal num_2 = 3.141592658;
QString str_2 = QString::num(num,'g',8);// 3.1415927
格式化输入

QString arg(const QString &a, int fieldWidth = 0, QChar fillChar = QLatin1Char( ’ ’ )) const

int age = 18;
QString name = "xaiomin";

// name 代替%1 age代替%2
QString str = QString("name is %1, age is %2").arg(name).arg(age);

qreal value = 123.456;
// 设置小数点后两位
str= QString("Number %1").arg(value,0,'f',2); // Number 123.45
与std::string互相转换
  • QString转std::string
QString qstr = "yiou";
std::string str = qstr.toStdString();
  • std::string 转QString
std::string str = "yoiu";
QString qstr = QString::fromStdString(str);

QByteArray

提供一个字节数组(序列),QByteArray可用于存储原始字节(包括“\ 0” )和传统的8位 “\ 0” 端接字符串 . 使用QByteArray比使用const char 更方便.
在IO操作中,c语言常使用const char ,而Qt中常使用QByteArray

初始化和访问
  • 批量初始化
QByteArray ba("Hello");
  • 按字节初始化 &访问
QByteArray ba;
ba.resize(5);
ba[0] = 0x30;
ba[1] = 0x31;
ba[2] = 0x32;
ba[3] = 0x33;
ba[4] = 0x34;

// 也可以使用at访问
QByteArray qArray;
qArray.resize(5);
qArray[0] = 0x30;
qArray[1] = 0x31;
qArray[2] = 0x32;
qArray[3] = 0x33;
qArray[4] = 0x34;
qDebug()<<qArray.at(3);
QByteArray 与char*相互转换
  • QByteArray转换成char*
QByteArray ba("Hello");
const char* str = ba.constData();
std::cout<<str<<std::endl;
  • char* 转换成QByteArray
// 第一种:通过QString的字符集转换
const char* p = "abc";
QString q = QString(p);
QByteArray ba = q.toUtf8();
qDebug()<<ba;

// 第二种:通过RawData(原始数据)
// const char hello[] = {'h', 'e', 'l', 'l', 'o'};
const char* hello = "hello";
QByteArray ba(QByteArray::fromRawData(hello,5))
关于\0的理解
QByteArray ba("hel\0l\0o",5);
std::cout << ba.size() <<std::endl; // 5
std::cout << ba.constData() << std::endl; // 遇到\0终止

QVariant

QVariant变量是没有数据类型的。 QVariant类像是最常见的Qt的数据类型的一个共用体(union),一个QVariant对象在一个时间只保存一个单一类型的一个单一的值(有些类型可能是多值的,比如字符串列表)。
可以使用toT()(T代表一种数据类型)函数来将QVariant对象转换为T类型,并且获取它的值。这里toT()函数会复制以前的QVariant对象,然后对其进行转换,所以以前的QVariant对象并不会改变。

容器

只要是数据就必须要使用容器,程序中的数据放在容器中方便增删改查。
Qt库提供了一组通用的基于模板的容器类(container classes)。这些容器类可以用来存储指定类型的项目(items),例如,如果大家需要一个QString类型的可变大小的数组,那么可以使用QVector(QString)。与STL(Standard Template Library,C++的标准模板库)中的容器类相比,Qt中的这些容器类更轻量,更安全,更容易使用。

容器只读遍历器读写遍历器
QList,QQueueQList::const_iteratorQList::iterator
QLinkedListQLinkedList::const_iteratorQLinkedList::iterator
QVector,QStackQVector::const_iteratorQVector::iterator
QSetQSet::const_iteratorQSet::iterator
QMap<Key, T>,QMultiMap<Key, T>QMap<Key, T>::const_iteratorQMap<Key, T>::iterator
QHash<Key, T>,QMultiHash<Key, T>QHash<Key, T>::const_iteratorQHash<Key, T>::iterator

STL风格迭代器兼容Qt和STL的通用算法(generic algorithms),而且在速度上进行了优化。对于每一个容器类,都有两个STL风格迭代器类型:一个提供了只读访问,另一个提供了读写访问。因为只读迭代器比读写迭代器要快很多,所以应尽可能使用只读迭代器
STL风格迭代器的API模仿了数组的指针,例如,使用“++”操作符来向后移动迭代器使其指向下一个项目;使用“*”操作符返回迭代器指向的项目等。需要说明的是,不同于Java风格迭代器,STL风格迭代器是直接指向项目的。其中一个容器的begin()函数返回了一个指向该容器中第一个项目的迭代器,end()函数也返回一个迭代器,但是这个迭代器指向该容器的最后一个项目的下一个假想的虚项目,end()标志着一个无效的位置,当列表为空时,begin()函数等价于end()函数。

QList

QList是一个模板类,它提供了一个列表。QList实际上是一个T类型项目的指针数组,所以它支持基于索引的访问,而且当项目的数目小于1000时,可以实现在列表中间进行快速的插入操作。QList提供了很多方便的接口函数来操作列表中的项目,例如:
插入操作insert();替换操作replace();移除操作removeAt();移动操作move();
交换操作swap();在表尾添加项目append();在表头添加项目prepend();
移除第一个项目removeFirst();移除最后一个项目removeLast()

从列表中移除一项并获取这个项目takeAt(),还有相应的takeFirst()和takeLast();
获取一个项目的索引indexOf();
判断是否含有相应的项目contains();
获取一个项目出现的次数count()。
对于QList,可以使用“<<”操作符来向列表中插入项目,也可以使用“[ ]”操作符通过索引来访问一个项目,其中项目是从0开始编号的。不过,对于只读的访问,另一种方法是使用at()函数,它比“[ ]”操作符要快很多。

void fun(){
    QList<int> qList;
    for (int i =0; i < 10; i++){
        qList.append(i); // 追加
    }
    qList.prepend(99);
    
    // for循环遍历
    for ( int i =0; i < qList.size(); i++){
        qDebug()<<qList.at(i);
        qDebug()<<qList[i];
    }
    
    // foreach
    foreach(int item, qList){
        qDebug()<<item;
    }
    
    // java风格迭代器 只读迭代器
    QListIterator<int> it(qList);
    while (it.hasNext()){
        qDebug()<< it.next();
    }
    
    // java风格迭代器 读写迭代器
    QMutableListIterator<int> mit(qList);
    while (mit.hasNext()) {
        if(mit.next() == 8){
            mit.setValue(888);
        }
    }
    
    // STL风格迭代器 只读迭代器
    QList<int>::const_iterator itm;
    for(itm = qList.constBegin(); itm != qList.constEnd(); itm++){
        qDebug()<<*itm;
    }
    
    // STL风格迭代器 读写迭代器
    QList<int>::iterator itm2;
    for(itm2 = qList.begin(); itm2 != qList.end(); itm2++){
        qDebug()<<*itm2;
        *itm2 = (*itm2)*9;
    }
    
}
int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);
    QList<QString> strList;
    QList<int> intList;

    strList.append("fuck");
    strList.append("a");
    strList.append("japan");
    strList.append("girl");

    intList << 6 << 8 << 9 << 9;

    QString str = strList.at(3);
    qDebug()<<strList.at(0) << " "
            <<strList.at(1) << " "
            <<strList.at(2) << " "
            <<strList.at(3) << " ";

    QList<QString>::const_iterator j;
    for (j = strList.constBegin(); j != strList.constEnd(); ++j)
    {
        qDebug() << *j;
    }
    return a.exec();
}
  QList<QString> list;
    list << "A" << "B" << "C" << "D";
    QList<QString>::iterator i; // 使用读写迭代器
    qDebug()<< "the forward is :";
    for(i = list.begin();i != list.end();i++){
        // 使用QString的toLower函数转换为小写
        *i = (*i).toLower();
        qDebug()<<*i;
    }

    qDebug()<<"the backward is :";
    while(i != list.begin()){
        // 到序遍历
        --i;
        qDebug()<<*i;
    }

    QList<QString>::const_iterator j; // 使用只读迭代器
    qDebug()<<"the foeward is :";
     for(j = list.constBegin(); j!= list.constEnd();j++){
         qDebug()<<*j;
     }

QLinkedList

基于迭代器访问的List,方便快速插入、删除

QLinkedList<int> list;
list << 1 << 2 << 3;
foreach(int i, list){
	qDebug() << i;
}

QVector

QVector又叫可变向量、可变数组

QMap

QMap类是一个容器类,它提供了一个基于跳跃列表的字典(a skip-list-based dictionary)。QMap是Qt的通用容器类之一,它存储(键,值)对并提供了与键相关的值的快速查找。QMap中提供了很多方便的接口函数,例如:
插入操作insert();
获取值value();
是否包含一个键contains();
删除一个键remove();
删除一个键并获取该键对应的值take();
清空操作clear();
插入一键多值insertMulti()。

可以使用“[ ]”操作符插入一个键值对或者获取一个键的值,不过当使用该操作符获取一个不存在的键的值时,会默认向map中插入该键,为了避免这个情况,可以使用value()函数来获取键的值。当使用value()函数时,如果指定的键不存在,那么默认会返回0,可以在使用该函数时提供参数来更改这个默认返回的值。QMap默认是一个键对应一个值的,但是也可以使用insertMulti()进行一键多值的插入,对于一键多值的情况,更方便的是使用QMap的子类QMultiMap。

void mapFun(){
    QMap<QString, int>map;
    map["one"] = 1; // 向map中插入("one",1)
    map["three"] = 3;
    map.insert("seven",7); // 使用insert()函数进行插入
    // 获取键的值,使用“[ ]”操作符时,如果map中没有该键,那么会自动插入
    int value1 = map["six"];
    qDebug() << "value1:" << value1;
    qDebug() << "contains 'six' ?" << map.contains("six");
    // 使用value()函数获取键的值,这样当键不存在时不会自动插入
    int value2 = map.value("five");
    qDebug() << "value2:" << value2;
    qDebug() << "contains 'five' ?" << map.contains("five");
    // 当键不存在时,value()默认返回0,这里可以设定该值,比如这里设置为9
    int value3 = map.value("nine",9);
    qDebug() << "value3:" << value3;
    
    // STL风格
    QList<int>::const_iterator itm;
    QMap<int,QString> Employees;
    Employees.insert(1,"Bob");
    Employees.insert(2,"Chad");
    Employees.insert(3,"Mary");
    Employees.insert(4,"oldWang");
    Employees[5] = "Danny"; //不推荐这样赋值
    QMap<int, QString>::const_iterator i = Employees.constBegin();
    while (i != Employees.constEnd()) {
        std::cout << i.key() << ": " << i.value().toStdString() << std::endl;
        ++i;
    }
    QMap<int, QString>::iterator i = Employees.begin();
    while (i != Employees.end()) {
        if(i.value() == "oldWang")        {
            i.value() = "robort";
        }
        ++i;
    }
}

QHash

QMap与QHash的差别:

  • QHash具有比QMap更快的查找速度
  • QHash以任意的顺序存储数据项,而QMap总是按照键Key顺序存储数据
  • QHash的键类型Key必须提供operator==()和一个全局的qHash(Key)函数,而QMap的键类型Key必须提供operator<()函数。
void hashFun(){
    QHash<int,QString> Employees;    
    Employees.insert(1,"Bob");    
    Employees.insert(2,"Chad");    
    Employees.insert(3,"Mary");    
    foreach(int i, Employees.keys())    
    {        
        qDebug() << Employees[i];   
    }    
    QHashIterator<int,QString> Iter(Employees); 
    while(Iter.hasNext())   
    {       
        Iter.next();   
        qDebug() << Iter.key() << " = " << Iter.value(); 
    }
}

注意:容器也可以嵌套使用,例如QMap<QString,QList >,这里键的类型是QString,而值的类型是QList,需要注意,在后面的“> >”符号之间要有一个空格,不然编译器会将它当做“>>”操作符对待。

  • 0
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

√沫影

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值