




版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報或認(rèn)領(lǐng)
文檔簡介
1、二十一、Qt數(shù)據(jù)庫(一)簡介(原創(chuàng))2010-03-02 12:03聲明:本文原創(chuàng)于yafeilinux的百度博客, 轉(zhuǎn)載請注明出處。從今天開始我們學(xué)習(xí)Qt數(shù)據(jù)庫編程的內(nèi)容。先說明:我們以后使用現(xiàn)在最新的基于Qt 的Qt Creator 1.3.1 Windows版本,該版本是2010年2月17日發(fā)布的。數(shù)據(jù)庫幾乎是每個較大的軟件所必須應(yīng)用的,而在Qt中也使用QtSql模塊實現(xiàn)了對數(shù)據(jù)庫的完美支持。我們在Qt Creator的幫助中查找QtSql Module,其內(nèi)容如下圖:可以看到這個模塊是一組類的集合,使用這個模塊我們需要加入頭文件#include <QtSql>,而在工程文件
2、中需要加入一行代碼:QT += sql這里每個類的作用在后面都有簡單的介紹,你也可以進(jìn)入其中查看其詳細(xì)內(nèi)容。下面我們先簡單的說一下QSqlDatabase類和QSqlQuery類。QSqlDatabase類實現(xiàn)了數(shù)據(jù)庫連接的操作,現(xiàn)在Qt支持的數(shù)據(jù)庫類型有如下幾種:而現(xiàn)在我們使用的免費的Qt只提供了SQLite和ODBC數(shù)據(jù)庫的驅(qū)動(我們可以在Qt Creator安裝目錄下的qtpluginssqldrivers文件夾下查看),而其他數(shù)據(jù)庫的驅(qū)動需要我們自己添加。SQLite是一個小巧的嵌入式數(shù)據(jù)庫,關(guān)于它的介紹你可以自己在網(wǎng)上查找。QSqlQuery類用來執(zhí)行SQL語句。(關(guān)于SQL語句:在
3、我的教程中只會出現(xiàn)很簡單的SQL語句,你沒有相關(guān)知識也可以看懂,但是如果想進(jìn)行深入學(xué)習(xí),就需要自己學(xué)習(xí)相關(guān)知識了。)下面我們就先利用這兩個類來實現(xiàn)最簡單的數(shù)據(jù)庫程序,其他的類我們會在以后的教程中逐個學(xué)習(xí)到。1.新建Qt控制臺工程。2.選擇上QtSql模塊,這樣就會自動往工程文件中添加QT += sql 這行代碼了。3.修改main.cpp中的內(nèi)容如下。#include <QtCore/QCoreApplication>#include <QtSql>int main(int argc, char *argv) QCoreApplica
4、tion a(argc, argv); QSqlDatabase db = QSqlDatabase:addDatabase("QSQLITE"); /添加數(shù)據(jù)庫驅(qū)動 db.setDatabaseName(":memory:"); /數(shù)據(jù)庫連接命名 if(!db.open() /打開數(shù)據(jù)庫 return false;
5、 QSqlQuery query; /以下執(zhí)行相關(guān)QSL語句 query.exec("create table student(id int primary key,name varchar)"); /新建student表,id設(shè)置為主鍵,還有一個name項 query.exec("insert into student values(1,'xiaogang')");
6、160; query.exec("insert into student values(2,'xiaoming')"); query.exec("insert into student values(3,'xiaohong')"); /向表中插入3條記錄 query.exec("select id,name from student where id >= 2");&
7、#160; /查找表中id >=2 的記錄的id項和name項的值 while(query.next() /query.next()指向查找到的第一條記錄,然后每次后移一條記錄 int ele0 = query.value(0).toInt(); /que
8、ry.value(0)是id的值,將其轉(zhuǎn)換為int型 QString ele1 =query.value(1).toString(); qDebug() << ele0 <<ele1 ; /輸出兩個值 return a.ex
9、ec();我們使用了SQLite數(shù)據(jù)庫,連接名為“:memory:”表示這是建立在內(nèi)存中的數(shù)據(jù)庫,也就是說該數(shù)據(jù)庫只在程序運行期間有效。如果需要保存該數(shù)據(jù)庫文件,我們可以將它更改為實際的文件路徑。4.最終效果如下。5.我們可以將主函數(shù)更改如下。int main(int argc, char *argv) QCoreApplication a(argc, argv); qDebug() << "Available drivers:" QStringList
10、drivers = QSqlDatabase:drivers(); foreach(QString driver, drivers) qDebug() << "t" << driver; return a.exec();這樣運行程序就可以顯示現(xiàn)在所有能用的數(shù)據(jù)庫驅(qū)動了??梢钥吹浆F(xiàn)在可用的數(shù)據(jù)庫驅(qū)動只有三個。二十二、Qt數(shù)據(jù)庫(二)添加MySQL數(shù)據(jù)庫驅(qū)動插件(原創(chuàng))2010-03-08 18:06聲明:本文原創(chuàng)于yafeilinux的百度博客,
11、 轉(zhuǎn)載請注明出處。在上一節(jié)的末尾我們已經(jīng)看到,現(xiàn)在可用的數(shù)據(jù)庫驅(qū)動只有3種,那么怎樣使用其他的數(shù)據(jù)庫呢?在Qt中,我們需要自己編譯其他數(shù)據(jù)庫驅(qū)動的代碼,讓它們以插件的形式來使用。下面我們就以現(xiàn)在比較流行的MySQL數(shù)據(jù)庫為例,說明一下怎樣在Qt Creator中添加數(shù)據(jù)庫驅(qū)動插件。在講述之前,我們先看一下Qt Creator中數(shù)據(jù)庫的插件到底放在哪里。我們進(jìn)入Qt Creator的安裝目錄,然后進(jìn)入相對應(yīng)的文件夾下,比方我這里是D:Qt2010.02.1qtpluginssqldrivers在這里我們可以看見幾個文件,如下圖:根據(jù)名字中的關(guān)鍵字,我們可以判斷出這就是ODBC數(shù)據(jù)庫和SQLite
12、數(shù)據(jù)庫的驅(qū)動插件。下面我們編譯好MySQL數(shù)據(jù)庫驅(qū)動后,也會在這里出現(xiàn)相對應(yīng)的文件。首先:我們查看怎樣安裝數(shù)據(jù)庫插件。我們打開Qt Creator,在幫助中搜索SQL Database Drivers關(guān)鍵字。這里列出了編譯Qt支持的所有數(shù)據(jù)庫的驅(qū)動的方法。我們下拉到在windows上編譯QMYSQL數(shù)據(jù)庫插件的部分,其內(nèi)容如下:這里詳細(xì)介紹了整個編譯的過程,其可以分為以下幾步:第一,下載MySQL的安裝程序,在安裝時選擇定制安裝,這時選中安裝Libs和Include文件。安裝位置可以是C:MySQL 。注意:安裝位置不建議改動,因為下面進(jìn)行編譯的命令中使用了安裝路徑,如果改動,那么下面也要進(jìn)行
13、相應(yīng)改動。第二,進(jìn)行編譯。我們按照實際情況輸入的命令如下。cd %QTDIR%srcpluginssqldriversmysqlqmake "INCLUDEPATH+=C:MySQLinclude" "LIBS+=C:MySQLliboptlibmysql.lib" mingw32-make注意:在上面的命令中qmake之后如果加上“-o Makefile”選項,那么這個插件只能在以release模式編譯程序時才能使用,所以我們上面沒有加這個選項。然后:我們按照上面的過程進(jìn)行相應(yīng)操作。1.我們先下載MySQL的安裝文件。我們可以到MyS
14、QL的官方主頁 進(jìn)行下載最新的MySQL的windows版本,現(xiàn)在具體的下載頁面地址為:我們不進(jìn)行注冊,直接點擊其下面的No thanks, just take me to the downloads!可以在其中選擇一個鏡像網(wǎng)點進(jìn)行下載,我使用的是Asia下的最后一個,就是臺灣的鏡像網(wǎng)點下載的。下載到的文件名為:mysql-essential-win32 ,其中的win32表明是32位的windows系統(tǒng),這一點一定要注意。文件大小為40M左右。當(dāng)然你也可以到中文網(wǎng)站上進(jìn)行下載:,隨便下一個windows的版本就行。2.安裝軟件。我們選擇定制安裝Custom。然后選中安裝Include文件和L
15、ib文件。我們將安裝路徑更改為:C:MySQL 。最終的界面如下。安裝完成后,我們不進(jìn)行任何操作,所以將兩個選項都取消。3.進(jìn)行編譯。我們在桌面上開始菜單中找到Qt Creator的菜單,然后打開Qt Command Prompt。然后輸入第一條命令cd %QTDIR%srcpluginssqldriversmysql 后按回車,運行效果如下。然后輸入第二條命令:qmake "INCLUDEPATH+=C:MySQLinclude" "LIBS+=C:MySQLliboptlibmysql.lib" 按回車后運行效果如下:最后輸入:mi
16、ngw32-make ,按下回車后經(jīng)過幾秒的編譯,最終效果如下:整個編譯過程中都沒有出現(xiàn)錯誤提示,可以肯定插件已經(jīng)編譯完成了。4.我們再次進(jìn)入Qt Creator安裝目錄下存放數(shù)據(jù)庫驅(qū)動插件的文件夾。我這里是D:Qt2010.02.1qtpluginssqldrivers其內(nèi)容如下:可以看到已經(jīng)有了和MySQL相關(guān)的文件了。最后:我們編寫程序測試插件。1.我們將上一次的主函數(shù)更改如下。int main(int argc, char *argv) QCoreApplication a(argc, argv); QSqlDat
17、abase db = QSqlDatabase:addDatabase("QMYSQL"); /添加數(shù)據(jù)庫驅(qū)動 return a.exec();運行程序,效果如下。這里提示:QSqlDatabase: QMYSQL driver not loaded 。2.這時我們需要將C:MySQLbin目錄下的libmySQL.dll文件復(fù)制到我們Qt Creator安裝目錄下的qtbin目錄中。如下圖:3.這時再運行程序,就沒有提示了。4.我們再將主函數(shù)更改一下,測試這時可用的數(shù)據(jù)庫驅(qū)動。int main(int argc, char *argv)
18、 QCoreApplication a(argc, argv); qDebug() << "Available drivers:" QStringList drivers = QSqlDatabase:drivers(); foreach(QString driver, drivers) qDebug() << "t" << driver;&
19、#160; return a.exec();運行效果如下:可以看到,現(xiàn)在已經(jīng)有了MySQL的數(shù)據(jù)庫驅(qū)動了。我們這里只介紹了MySQL驅(qū)動插件在windows下的編譯方法,其他數(shù)據(jù)庫和其他平臺的編譯方法可以按照幫助中的說明進(jìn)行,我們不再介紹。其實Qt不僅可以編譯現(xiàn)成的數(shù)據(jù)庫驅(qū)動插件,我們也可以編寫自己的數(shù)據(jù)庫驅(qū)動插件,當(dāng)然這是一件相當(dāng)復(fù)雜的事情,我們這里也就不再進(jìn)行介紹。關(guān)于MySQL的使用,我們的教程里現(xiàn)在不再涉及,在 這里有MySQL的中文參考手冊,你可以進(jìn)行參考。二十三、Qt數(shù)據(jù)庫(三)利用QSqlQuery類執(zhí)行SQL語句(一)(原創(chuàng))2010-03-11 23:
20、22聲明:本文原創(chuàng)于yafeilinux的百度博客, 轉(zhuǎn)載請注明出處。SQL即結(jié)構(gòu)化查詢語言,是關(guān)系數(shù)據(jù)庫的標(biāo)準(zhǔn)語言。前面已經(jīng)提到,在Qt中利用QSqlQuery類實現(xiàn)了執(zhí)行SQL語句。需要說明,我們這里只是Qt教程,而非專業(yè)的數(shù)據(jù)庫教程,所以我們不會對數(shù)據(jù)庫中的一些知識進(jìn)行深入講解,下面只是對最常用的幾個知識點進(jìn)行講解。我們下面先建立一個工程,然后講解四個知識點,分別是:query.exec("select * from zb_tb where zd_bs like '"+ aValue + "%' order by zf_bfb desc&qu
21、ot;); 一,操作SQL語句返回的結(jié)果集。二,在SQL語句中使用變量。三,批處理操作。四,事務(wù)操作。我們新建Qt4 Gui Application工程,我這里工程名為query ,然后選中QtSql模塊,Base class選QWidget。工程建好后,添加C+ Header File ,命名為connection.h ,更改其內(nèi)容如下:#ifndef CONNECTION_H#define CONNECTION_H#include <QMessageBox>#include <QSqlDatabase>#include <QSqlQuery>static
22、 bool createConnection() QSqlDatabase db = QSqlDatabase:addDatabase("QSQLITE"); db.setDatabaseName(":memory:"); if (!db.open() QMessageBox:critical(0, qApp->tr("Cannot open da
23、tabase"), qApp->tr("Unable to establish a database connection." ), QMessageBox:Cancel);
24、60; return false; QSqlQuery query; query.exec("create table student (id int primary key, " "name varchar(20)");
25、 query.exec("insert into student values(0, 'first')"); query.exec("insert into student values(1, 'second')"); query.exec("insert into student values(2, 'third')"); query.exec
26、("insert into student values(3, 'fourth')"); query.exec("insert into student values(4, 'fifth')"); return true;#endif / CONNECTION_H然后更改main.cpp的內(nèi)容如下:#include <QtGui/QApplication>#include "widget.h"#include "
27、;connection.h"int main(int argc, char *argv) QApplication a(argc, argv); if (!createConnection() return 1; Widget w; w.show();
28、; return a.exec();可以看到,我們是在主函數(shù)中打開數(shù)據(jù)庫的,而數(shù)據(jù)庫連接用一個函數(shù)完成,并單獨放在一個文件中,這樣的做法使得主函數(shù)很簡潔。我們今后使用數(shù)據(jù)庫時均使用這種方法。我們打開數(shù)據(jù)庫連接后,新建了一個學(xué)生表,并在其中插入了幾條記錄。表中的一行就叫做一條記錄,一列是一個屬性。這個表共有5條記錄,id和name兩個屬性。程序中的“id int primary key”表明id屬性是主鍵,也就是說以后添加記錄時,必須有id項。下面我們打開widget.ui文件,在設(shè)計器中向界面上添加一個Push Button ,和一個Spin Box 。將按鈕的文本改為“查詢”,然后進(jìn)入其單擊
29、事件槽函數(shù),更改如下。void Widget:on_pushButton_clicked() QSqlQuery query; query.exec("select * from student"); while(query.next() qDebug() << query.value(0).toInt() << query
30、.value(1).toString(); 我們在widget.cpp中添加頭文件:#include <QSqlQuery>#include <QtDebug>然后運行程序,單擊“查詢”按鈕,效果如下:可以看到在輸出窗口,表中的所有內(nèi)容都輸出出來了。這表明我們的數(shù)據(jù)庫連接已經(jīng)成功建立了。一,操作SQL語句返回的結(jié)果集。在上面的程序中,我們使用query.exec("select * from student");來查詢出表中所有的內(nèi)容。其中的SQL語句“select * from student”中“*”號表明查詢
31、表中記錄的所有屬性。而當(dāng)query.exec("select * from student");這條語句執(zhí)行完后,我們便獲得了相應(yīng)的執(zhí)行結(jié)果,因為獲得的結(jié)果可能不止一條記錄,所以我們稱之為結(jié)果集。結(jié)果集其實就是查詢到的所有記錄的集合,而在QSqlQuery類中提供了多個函數(shù)來操作這個集合,需要注意這個集合中的記錄是從0開始編號的。最常用的有:seek(int n) :query指向結(jié)果集的第n條記錄。first() :query指向結(jié)果集的第一條記錄。last() :query指向結(jié)果集的最后一條記錄。next() :query指向下一條記錄,每執(zhí)行一次該函數(shù),便指向相鄰的
32、下一條記錄。previous() :query指向上一條記錄,每執(zhí)行一次該函數(shù),便指向相鄰的上一條記錄。record() :獲得現(xiàn)在指向的記錄。value(int n) :獲得屬性的值。其中n表示你查詢的第n個屬性,比方上面我們使用“select * from student”就相當(dāng)于“select id, name from student”,那么value(0)返回id屬性的值,value(1)返回name屬性的值。該函數(shù)返回QVariant類型的數(shù)據(jù),關(guān)于該類型與其他類型的對應(yīng)關(guān)系,可以在幫助中查看QVariant。at() :獲得現(xiàn)在query指向的記錄在結(jié)果集中的編號。需要說明,當(dāng)剛
33、執(zhí)行完query.exec("select * from student");這行代碼時,query是指向結(jié)果集以外的,我們可以利用query.next(),當(dāng)?shù)谝淮螆?zhí)行這句代碼時,query便指向了結(jié)果集的第一條記錄。當(dāng)然我們也可以利用seek(0)函數(shù)或者first()函數(shù)使query指向結(jié)果集的第一條記錄。但是為了節(jié)省內(nèi)存開銷,推薦的方法是,在query.exec("select * from student");這行代碼前加上query.setForwardOnly(true);這條代碼,此后只能使用next()和seek()函數(shù)。下面將“查詢”
34、按鈕的槽函數(shù)更改如下:void Widget:on_pushButton_clicked() QSqlQuery query; query.exec("select * from student"); qDebug() << "exec next() :" if(query.next() /開始就先執(zhí)行一次next()函數(shù),那么query指向結(jié)果集的第一條記錄
35、60; int rowNum = query.at(); /獲取query所指向的記錄在結(jié)果集中的編號 int columnNum = query.record().count(); /獲取每條記錄中屬性(即列)的個數(shù)
36、0; int fieldNo = query.record().indexOf("name"); /獲取"name"屬性所在列的編號,列從左向右編號,最左邊的編號為0 int id = query.value(0).toInt(); /獲取id屬性
37、的值,并轉(zhuǎn)換為int型 QString name = query.value(fieldNo).toString(); /獲取name屬性的值 qDebug() << "rowNum is : " << rowNum /將結(jié)果輸出 &
38、#160; << " id is : " << id << " name is : " << name &
39、#160; << " columnNum is : " << columnNum; qDebug() << "exec seek(2) :" if(query.seek(2) /定位到結(jié)果集中編號為2的記錄,即第三條記錄,因為第一條記錄的編號為0
40、; qDebug() << "rowNum is : " << query.at() << " id is : " << query.value(0).toInt()
41、; << " name is : " << query.value(1).toString(); qDebug() << "exec last() :" if(query.last() /定位到結(jié)果集中最后一條記錄 qDebug()
42、 << "rowNum is : " << query.at() << " id is : " << query.value(0).toInt() &l
43、t;< " name is : " << query.value(1).toString(); 然后在widget.cpp文件中添加頭文件。#include <QSqlRecord>運行程序,結(jié)果如下:二十四、Qt數(shù)據(jù)庫(四)利用QSqlQuery類執(zhí)行SQL語句(二)(原創(chuàng))2010-03-12 21:51聲明:本文原創(chuàng)于yafeilinux的百度博客, 轉(zhuǎn)載請注明出處。接著上一篇教程。二,在SQL語句中使用變量。我們先看下面的一個例子,將“查詢”按鈕的槽函數(shù)更改如下:void Widget:on_push
44、Button_clicked() QSqlQuery query; query.prepare("insert into student (id, name) " "values (:id, :name)"); query.bindValue(0,
45、 5); query.bindValue(1, "sixth"); query.exec(); /下面輸出最后一條記錄 query.exec("select * from student"); query.last(); int id = query.value(0).toInt(); QString na
46、me = query.value(1).toString(); qDebug() << id << name;運行效果如下:可以看到,在student表的最后又添加了一條記錄。在上面的程序中,我們先使用了prepare()函數(shù),在其中利用了“:id”和“:name”來代替具體的數(shù)據(jù),而后又利用bindValue()函數(shù)給id和name兩個屬性賦值,這稱為綁定操作。其中編號0和1分別代表“:id”和“:name”,就是說按照prepare()函數(shù)中出現(xiàn)的屬性從左到右編號,最左邊是0 。這里的“:id”和“:name”,叫做占位符,這是O
47、DBC數(shù)據(jù)庫的表示方法,還有一種Oracle的表示方法就是全部用“?”號。如下:query.prepare("insert into student (id, name) " "values (?, ?)");query.bindValue(0, 5);query.bindValue(1, "sixth");query.exec();
48、我們也可以利用addBindValue()函數(shù),這樣就可以省去編號,它是按順序給屬性賦值的,如下:query.prepare("insert into student (id, name) " "values (?, ?)");query.addBindValue(5);query.addBindValue("sixth");quer
49、y.exec();當(dāng)用ODBC的表示方法時,我們也可以將編號用實際的占位符代替,如下:query.prepare("insert into student (id, name) " "values (:id, :name)");query.bindValue(":id", 5);quer
50、y.bindValue(":name", "sixth");query.exec();以上各種形式的表示方式效果是一樣的。特別注意,在最后一定要執(zhí)行exec()函數(shù),所做的操作才能被真正執(zhí)行。下面我們就可以利用綁定操作在SQL語句中使用變量了。void Widget:on_pushButton_clicked() QSqlQuery query; query.prepare("select name from student where id = ?");
51、0; int id = ui->spinBox->value(); /從界面獲取id的值 query.addBindValue(id); /將id值進(jìn)行綁定 query.exec(); query.next(); /指向第一條記錄 qDebug() << query.value(0).toString();運行程序,效果如下:我們改變spinBox的數(shù)值大小,然后按下“查詢”按鈕,可以看到對應(yīng)的結(jié)果就出來
52、了。三,批處理操作。當(dāng)要進(jìn)行多條記錄的操作時,我們就可以利用綁定進(jìn)行批處理??聪旅娴睦?。void Widget:on_pushButton_clicked() QSqlQuery q; q.prepare("insert into student values (?, ?)"); QVariantList ints; ints << 10 << 11 << 12 << 13;
53、0; q.addBindValue(ints); QVariantList names; names << "xiaoming" << "xiaoliang" << "xiaogang" << QVariant(QVariant:String); /最后一個是空字符串,應(yīng)與前面的格式相同 q.addBindValue(names);&
54、#160; if (!q.execBatch() /進(jìn)行批處理,如果出錯就輸出錯誤 qDebug() << q.lastError(); /下面輸出整張表 QSqlQuery query; query.exec("select * from student"); while(query.next()
55、160; int id = query.value(0).toInt(); QString name = query.value(1).toString(); qDebug() << id << name; 然后在widget.cpp文件中添加頭文件 #include &l
56、t;QSqlError> 。我們在程序中利用列表存儲了同一屬性的多個值,然后進(jìn)行了值綁定。最后執(zhí)行execBatch()函數(shù)進(jìn)行批處理。注意程序中利用QVariant(QVariant:String)來輸入空值NULL,因為前面都是QString類型的,所以這里要使用QVariant:String 使格式一致化。運行效果如下:四,事務(wù)操作。事務(wù)是數(shù)據(jù)庫的一個重要功能,所謂事務(wù)是用戶定義的一個數(shù)據(jù)庫操作序列,這些操作要么全做要么全不做,是一個不可分割的工作單位。在Qt中用transaction()開始一個事務(wù)操作,用commit()函數(shù)或rollback()函數(shù)進(jìn)行
57、結(jié)束。commit()表示提交,即提交事務(wù)的所有操作。具體地說就是將事務(wù)中所有對數(shù)據(jù)庫的更新寫回到數(shù)據(jù)庫,事務(wù)正常結(jié)束。rollback()表示回滾,即在事務(wù)運行的過程中發(fā)生了某種故障,事務(wù)不能繼續(xù)進(jìn)行,系統(tǒng)將事務(wù)中對數(shù)據(jù)庫的所有已完成的操作全部撤銷,回滾到事務(wù)開始時的狀態(tài)。如下面的例子:void Widget:on_pushButton_clicked() if(QSqlDatabase:database().driver()->hasFeature(QSqlDriver:Transactions) &
58、#160; /先判斷該數(shù)據(jù)庫是否支持事務(wù)操作 QSqlQuery query; if(QSqlDatabase:database().transaction() /啟動事務(wù)操作 /
59、; /下面執(zhí)行各種數(shù)據(jù)庫操作 query.exec("insert into student values (14, 'hello')"); query.exec("de
60、lete from student where id = 1"); / if(!QSqlDatabase:database().commit()
61、 qDebug() << QSqlDatabase:database().lastError(); /提交 if(!QSqlDatabase:database().rollback()
62、0; qDebug() << QSqlDatabase:database().lastError(); /回滾 /輸出整張表
63、160; query.exec("select * from student"); while(query.next() qDebug() << query.value(0).toInt() << query.value(1).toString(); 然后
64、在widget.cpp文件中添加頭文件 #include <QSqlDriver> 。QSqlDatabase:database()返回程序前面所生成的連接的QSqlDatabase對象。hasFeature()函數(shù)可以查看一個數(shù)據(jù)庫是否支持事務(wù)。運行結(jié)果如下:可以看到結(jié)果是正確的。對SQL語句我們就介紹這么多,其實Qt中提供了更為簡單的不需要SQL語句就可以操作數(shù)據(jù)庫的方法,我們在下一節(jié)講述這些內(nèi)容。二十五、Qt數(shù)據(jù)庫(五)QSqlQueryModel(原創(chuàng))2010-03-22 21:11聲明:本文原創(chuàng)于yafeilinux的百度博客, 轉(zhuǎn)載請注明出處。在上一篇的最后我們說到,
65、Qt中使用了自己的機(jī)制來避免使用SQL語句,它為我們提供了更簡單的數(shù)據(jù)庫操作和數(shù)據(jù)顯示模型。它們分別是只讀的QSqlQueryModel,操作單表的QSqlTableModel和以及可以支持外鍵的QSqlRelationalTableModel。這次我們先講解QSqlQueryModel。QSqlQueryModel類為SQL的結(jié)果集提供了一個只讀的數(shù)據(jù)模型,下面我們先利用這個類進(jìn)行一個最簡單的操作。我們新建Qt4 Gui Application工程,我這里工程名為queryModel ,然后選中QtSql模塊,Base class選QWidget。工程建好后,添加C+ Header File
66、 ,命名為database.h,更改其內(nèi)容如下:#ifndef DATABASE_H#define DATABASE_H#include <QSqlDatabase>#include <QSqlQuery>static bool createConnection() QSqlDatabase db = QSqlDatabase:addDatabase("QSQLITE"); db.setDatabaseName("database.db");
67、60; if(!db.open() return false; QSqlQuery query; query.exec("create table student (id int primary key, name vchar)"); query.exec("insert into student values (0,'yafei0')"); query.exec("inse
68、rt into student values (1,'yafei1')"); query.exec("insert into student values (2,'yafei2')"); return true;#endif / DATABASE_H這里我們使用了db.setDatabaseName("database.db"); ,我們沒有再使用以前的內(nèi)存數(shù)據(jù)庫,而是使用了真實的文件,這樣后面對數(shù)據(jù)庫進(jìn)行的操作就能保存下來了。然后進(jìn)入mai
69、n.cpp,將其內(nèi)容更改如下:#include <QtGui/QApplication>#include "widget.h"#include "database.h"int main(int argc, char *argv) QApplication a(argc, argv); if(!createConnection() return 1; Wi
70、dget w; w.show(); return a.exec();下面我們在widget.ui中添加一個顯示為“查詢”的Push Button,并進(jìn)入其單擊事件槽函數(shù),更改如下:void Widget:on_pushButton_clicked() QSqlQueryModel *model = new QSqlQueryModel; model->setQuery("select * from student");
71、0; model->setHeaderData(0, Qt:Horizontal, tr("id"); model->setHeaderData(1, Qt:Horizontal, tr("name"); QTableView *view = new QTableView; view->setModel(model); view->show();我們新建了QSqlQ
72、ueryModel類對象model,并用setQuery()函數(shù)執(zhí)行了SQL語句“("select * from student");”用來查詢整個student表的內(nèi)容,可以看到,該類并沒有完全避免SQL語句。然后我們設(shè)置了表中屬性顯示時的名字。最后我們建立了一個視圖view,并將這個model模型關(guān)聯(lián)到視圖中,這樣數(shù)據(jù)庫中的數(shù)據(jù)就能在窗口上的表中顯示出來了。我們在widget.cpp中添加頭文件:#include <QSqlQueryModel>#include <QTableView> 我們運行程序,并按下“查詢”按鍵,效果如下:我們在工程文件
73、夾下查看數(shù)據(jù)庫文件:下面我們利用這個模型來操作數(shù)據(jù)庫。1.我們在void Widget:on_pushButton_clicked()函數(shù)中添加如下代碼:int column = model->columnCount(); /獲得列數(shù)int row = model->rowCount(); / 獲得行數(shù)QSqlRecord record = model->record(1); /獲得一條記錄QModelIndex index = model->index(1,1); /獲得一條記錄的一個屬性的值qDebug()
74、 << "column num is:" << column << endl << "row num is:" << row << endl <<"the second record is:"
75、 << record << endl << "the data of index(1,1) is:"<< index.data();在我們在widget.cpp中添加頭文件:#include <QSqlRecord>#include <QModelIndex>#include <QDebug>此時運行程序,效果如下:2.當(dāng)然我們在這里也可以使用前面介紹過的que
76、ry執(zhí)行SQL語句。例如我們在void Widget:on_pushButton_clicked()函數(shù)中添加如下代碼:QSqlQuery query = model->query();query.exec("select name from student where id = 2 ");query.next();qDebug() << query.value(0).toString();這樣就可以輸出表中的值了,你可以運行程序測試一下。3.當(dāng)我們將函數(shù)改為如下。void Widget:on_pushButton_clicked()
77、; QSqlQueryModel *model = new QSqlQueryModel; model->setQuery("select * from student"); model->setHeaderData(0, Qt:Horizontal, tr("id"); model->setHeaderData(1, Qt:Horizontal, tr("name");
78、160; QTableView *view = new QTableView; view->setModel(model); view->show(); QSqlQuery query = model->query(); query.exec("insert into student values (10,'yafei10')"); /插入一條記錄這時我們運行程
79、序,效果如下:我們發(fā)現(xiàn)表格中并沒有增加記錄,怎么回事呢?我們關(guān)閉程序,再次運行,效果如下:發(fā)現(xiàn)這次新的記錄已經(jīng)添加了。在上面我們執(zhí)行了添加記錄的SQL語句,但是在添加記錄之前,就已經(jīng)進(jìn)行顯示了,所以我們的更新沒能動態(tài)的顯示出來。為了能讓其動態(tài)地顯示我們的更新,我們可以將函數(shù)更改如下:void Widget:on_pushButton_clicked() QSqlQueryModel *model = new QSqlQueryModel; model->setQuery("select * from student"); model->setHeaderData(0, Qt:Horizontal, tr("id"); model->setHeaderData(1, Qt:
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 回遷工作經(jīng)費管理辦法
- 余杭房屋租賃管理辦法
- 請假休假管理:全面指南與實施建議
- 安全生產(chǎn)與文明施工綜合實施方案
- 公司個人借支管理辦法
- 農(nóng)場人口管理辦法細(xì)則
- 安全生產(chǎn)責(zé)任書模版
- 行政違法的處罰方式
- 建設(shè)工程項目應(yīng)當(dāng)配備專職安全生產(chǎn)管理人員
- 商業(yè)思維在教育機(jī)構(gòu)線上活動策劃中的應(yīng)用研究
- 拍賣公司員工培訓(xùn)考核管理制度
- 廣東省行業(yè)企業(yè)職業(yè)技能競賽技術(shù)工作指引
- 2025年貴州省中考語文試卷真題(含答案)
- 浙江2025年6月高一學(xué)考模擬歷史試題及答案
- 2025年計算機(jī)程序設(shè)計考試試卷及答案
- 2025年河南省中考數(shù)學(xué)真題含答案
- 人力中介公司管理制度
- 抗精神病藥氯丙嗪講課件
- 2025人教英語初中八年級下冊期末測試卷(含答案)
- 燃?xì)馊霊艋卦L管理制度
-
評論
0/150
提交評論