hejialiangya 发表于 2023-4-11 11:39:01

嗨嗨嗨,又是我,新手又有问题出现,求大神帮忙

写了个查询界面,sql语句查询结果正常,sql_result输出结果是x行10列,
https://t3.wodetu.cn/2023/04/11/ca86f709bae6047f01feded880cd9f07.png

我的需求如下
https://t4.wodetu.cn/2023/04/11/a50c2e5dd7c9fa9b36d7332d265e33e9.png

我想QTableView.setmodel(sql_resule)
https://t1.wodetu.cn/2023/04/11/5b4957d4ef00b5f94af4cd2c8c8c3fd7.png

只能用for循环一个一个单元格添加数据么?有简单点的办法么?

isdkz 发表于 2023-4-11 11:44:33

要将 SQL 查询结果放入 QTableView 中,您可以使用 QSqlTableModel 或 QSqlQueryModel 作为模型。

这些模型可以处理 SQL 查询结果,将其转换为适合 QTableView 显示的格式。这样您就不需要使用 for 循环逐个添加数据了。

首先,确保您已经从 PyQt5.QtSql 模块导入了 QSqlQueryModel 和 QSqlDatabase:

from PyQt5.QtSql import QSqlQueryModel, QSqlDatabase

然后,您可以按照以下步骤将查询结果设置为 QTableView 的模型:


[*]使用您的数据库连接创建一个 QSqlDatabase 实例。
[*]创建一个 QSqlQueryModel 实例。
[*]设置 QSqlQueryModel 实例的查询。
[*]将 QSqlQueryModel 实例设置为 QTableView 的模型。


示例代码:

from PyQt5.QtWidgets import QApplication, QTableView
from PyQt5.QtSql import QSqlQueryModel, QSqlDatabase

app = QApplication([])

# 1. 创建 QSqlDatabase 实例
db = QSqlDatabase.addDatabase("QSQLITE")# 或使用您的数据库类型
db.setDatabaseName("your_database_name.db")# 使用您的数据库名
db.open()

# 2. 创建 QSqlQueryModel 实例
model = QSqlQueryModel()

# 3. 设置 QSqlQueryModel 实例的查询
query = "SELECT * FROM your_table_name"# 使用您的 SQL 查询和表名
model.setQuery(query)

# 4. 将 QSqlQueryModel 实例设置为 QTableView 的模型
view = QTableView()
view.setModel(model)
view.show()

app.exec_()

替换上述代码中的占位符(如 "your_database_name.db" 和 "your_table_name")为您实际使用的数据库名和表名。

这样,您就可以直接将 SQL 查询结果设置为 QTableView 的模型,而无需逐个添加数据。

hejialiangya 发表于 2023-4-11 14:35:43

isdkz 发表于 2023-4-11 11:44
要将 SQL 查询结果放入 QTableView 中,您可以使用 QSqlTableModel 或 QSqlQueryModel 作为模型。

这些 ...

我的数据库连接信息是单独写在Dbconnect.py里的,如果用到查询就import Dbconnect
Dbconnect.py 代码如下

import oracledb
import os

# 初始化Oracle客户端,启用thick模式
oracledb.init_oracle_client(lib_dir=r"C:\instantclient_11_2")

# 连接oracle数据库
try:
    conn = oracledb.connect(
      host="130.1.10.241",
      port=1521,
      user="XXK",
      password="888xxk",
      service_name="orcl"
      )
    cursor = conn.cursor()
except:
    print("数据库连接失败!")

我头文件import了之后,请问还需要创建 QSqlDatabase 实例吗?如果需要应该怎么写,是这样写吗?
db = QSqlDatabase.addDatabase("QOracle")# 或使用您的数据库类型
db.setDatabaseName("xxk.db")# 使用您的数据库名
db.open()

isdkz 发表于 2023-4-11 14:39:45

hejialiangya 发表于 2023-4-11 14:35
我的数据库连接信息是单独写在Dbconnect.py里的,如果用到查询就import Dbconnect
Dbconnect.py 代码如 ...

了解您的情况了,如果您已经使用 oracledb 建立了数据库连接,那么您可以使用 QSqlQueryModel 来直接执行查询并将结果显示在 QTableView 中。

在这种情况下,您不需要创建 QSqlDatabase 实例。请确保您已经从 PyQt5.QtSql 模块导入了 QSqlQueryModel。

您可以按照以下步骤将查询结果设置为 QTableView 的模型:


[*]使用您的数据库连接创建一个 QSqlQueryModel 实例。
[*]设置 QSqlQueryModel 实例的查询。
[*]将 QSqlQueryModel 实例设置为 QTableView 的模型。


示例代码:

from PyQt5.QtWidgets import QApplication, QTableView
from PyQt5.QtSql import QSqlQueryModel
import Dbconnect

app = QApplication([])

# 1. 创建 QSqlQueryModel 实例
model = QSqlQueryModel()

# 2. 设置 QSqlQueryModel 实例的查询
query = "SELECT * FROM your_table_name"# 使用您的 SQL 查询和表名
model.setQuery(query, Dbconnect.conn)# 使用您的数据库连接

# 3. 将 QSqlQueryModel 实例设置为 QTableView 的模型
view = QTableView()
view.setModel(model)
view.show()

app.exec_()

替换上述代码中的占位符(如 "your_table_name")为您实际使用的表名。

这样,您就可以直接将 SQL 查询结果设置为 QTableView 的模型,而无需逐个添加数据。

hejialiangya 发表于 2023-4-11 15:29:43

isdkz 发表于 2023-4-11 14:39
了解您的情况了,如果您已经使用 oracledb 建立了数据库连接,那么您可以使用 QSqlQueryModel 来直接执行 ...

您好,您的第二步,我查询为什么总是没有结果https://t4.wodetu.cn/2023/04/11/3ce73c8b48ed367398da9ef3e713d9dc.png

isdkz 发表于 2023-4-11 15:42:44

hejialiangya 发表于 2023-4-11 15:29
您好,您的第二步,我查询为什么总是没有结果

setQuery 方法是用于在 QSqlQueryModel 中设置一个 SQL 查询语句的。

它主要用于从数据库中获取数据并将这些数据存储在模型中,以便在视图(如 QTableView)中显示。这个方法没有返回值。这跟你直接打印 cursor.execute 的执行结果也为空一样的道理,cursor执行后还得用 fetchall 把结果取出来

具体而言,当您调用 setQuery 方法时,它将执行 SQL 查询,并将查询结果存储在模型中。这使得您可以将 QSqlQueryModel 实例关联到 QTableView,从而自动显示查询结果。

下面是一个简单的示例,说明如何使用 QSqlQueryModel 和 setQuery:

from PyQt5.QtWidgets import QApplication, QTableView
from PyQt5.QtSql import QSqlDatabase, QSqlQueryModel

app = QApplication([])

# 连接数据库
db = QSqlDatabase.addDatabase("QSQLITE")
db.setDatabaseName("your_database_name.db")
db.open()

# 创建 QSqlQueryModel 实例
model = QSqlQueryModel()

# 设置 QSqlQueryModel 实例的查询
query = "SELECT * FROM your_table_name"
model.setQuery(query)

# 将 QSqlQueryModel 实例设置为 QTableView 的模型
view = QTableView()
view.setModel(model)
view.show()

app.exec_()

在这个示例中,model.setQuery(query) 将执行查询并将结果存储在模型中。然后,通过将模型设置为 QTableView 的模型,您可以在视图中看到查询结果。

也可以用以下方法获取查询结果:

在使用 setQuery 方法设置查询后,您可以使用 QSqlQueryModel 的一些方法来查看查询结果。例如,您可以使用 rowCount() 和 columnCount() 方法来查看查询结果中的行数和列数,还可以使用 record() 和 data() 方法来检索特定单元格的数据。

以下是一个示例,说明如何在调用 setQuery 之后查看查询结果:

from PyQt5.QtWidgets import QApplication, QTableView
from PyQt5.QtSql import QSqlDatabase, QSqlQueryModel

app = QApplication([])

# 连接数据库
db = QSqlDatabase.addDatabase("QSQLITE")
db.setDatabaseName("your_database_name.db")
db.open()

# 创建 QSqlQueryModel 实例
model = QSqlQueryModel()

# 设置 QSqlQueryModel 实例的查询
query = "SELECT * FROM your_table_name"
model.setQuery(query)

# 获取查询结果的行数和列数
row_count = model.rowCount()
column_count = model.columnCount()
print(f"查询结果有 {row_count} 行,{column_count} 列。")

# 遍历查询结果并打印每个单元格的数据
for row in range(row_count):
    for col in range(column_count):
      cell_data = model.data(model.index(row, col))
      print(f"({row}, {col}): {cell_data}")

# 将 QSqlQueryModel 实例设置为 QTableView 的模型
view = QTableView()
view.setModel(model)
view.show()

app.exec_()

这个示例将遍历查询结果,并打印每个单元格的数据。注意,QSqlQueryModel 通常与视图(如 QTableView)一起使用,可以自动显示查询结果。因此,在实际应用中,您可能不需要手动查看和处理查询结果,而是将其直接显示在视图中。

hejialiangya 发表于 2023-4-11 16:19:12

本帖最后由 hejialiangya 于 2023-4-11 16:20 编辑

isdkz 发表于 2023-4-11 15:42
setQuery 方法是用于在 QSqlQueryModel 中设置一个 SQL 查询语句的。

它主要用于从数据库中获取数据 ...

谢大佬不厌其烦讲解,原理讲的很透,有点懂了。
我试了下查询结果行列检测,怀疑是不是因为我查询没有关联数据库?
在已有Dbconnect.py的前提下需要再指定数据库连接么?
我学着你的方法加了DB连接,发现还是0行0列,是不是我写的有问题
https://t3.wodetu.cn/2023/04/11/e78acb95e2b86b447a1426fcbdca1a57.png

isdkz 发表于 2023-4-11 16:37:58

hejialiangya 发表于 2023-4-11 16:19
谢大佬不厌其烦讲解,原理讲的很透,有点懂了。
我试了下查询结果行列检测,怀疑是不是因为我查询没有 ...

确实,要使 QSqlQueryModel 正确执行查询并返回结果,您需要确保已正确连接到数据库。在您的情况下,您需要使用 Qt 提供的 Oracle 支持(QOCI)来连接到数据库。

首先,请确保您已安装 Qt 的 Oracle 数据库驱动程序。然后,使用以下代码连接到数据库:

from PyQt5.QtSql import QSqlDatabase

db = QSqlDatabase.addDatabase("QOCI")
db.setHostName("130.1.10.241")
db.setPort(1521)
db.setDatabaseName("orcl")
db.setUserName("XXK")
db.setPassword("888xxk")

if db.open():
    print("数据库连接成功")
else:
    print("数据库连接失败")

请注意,这里我们使用 setHostName、setPort、setDatabaseName、setUserName 和 setPassword 方法设置连接参数,而不是 setDatabaseName。

一旦您连接到数据库,请确保在设置 QSqlQueryModel 查询时将数据库连接传递给 setQuery 方法,如下所示:

model.setQuery(query, db)

这将确保查询在正确的数据库连接上执行,并返回预期的结果。

如果问题仍然存在,您可以检查 QSqlQueryModel 中的错误,以便了解查询执行过程中的任何问题。

要检查错误,请使用 model.lastError() 方法,例如:

error = model.lastError()
if error.isValid():
    print(f"查询错误: {error.text()}")
else:
    print("查询成功")

hejialiangya 发表于 2023-4-12 11:30:57

isdkz 发表于 2023-4-11 16:37
确实,要使 QSqlQueryModel 正确执行查询并返回结果,您需要确保已正确连接到数据库。在您的情况下,您需 ...

今天试了一下,调试--【控制台】提示:

数据库连接失败
查询错误: Driver not loaded Driver not loaded

isdkz 发表于 2023-4-12 12:58:36

hejialiangya 发表于 2023-4-12 11:30
今天试了一下,调试--【控制台】提示:

数据库连接失败


看起来您遇到了驱动程序未加载的问题。

这可能是由于 Qt 未正确安装 QOCI 驱动程序,或者驱动程序未找到导致的。

首先,请确保您已安装 Qt 的 Oracle 数据库驱动程序。如果您使用的是预编译的 Qt 安装包,它可能不包含 QOCI 驱动程序。

您可以通过查看 plugins/sqldrivers 目录来检查驱动程序是否存在。如果不存在,您需要从源代码编译 Qt 以包含 QOCI 驱动程序。

有关如何构建和安装 Qt Oracle 驱动程序的详细信息,请参阅官方文档:


[*]Qt for Oracle (QOCI)


接下来,请确保您已正确设置环境变量以指向 Oracle 客户端库。

您可能需要设置 ORACLE_HOME 和 LD_LIBRARY_PATH(Linux)或 PATH(Windows)环境变量。

例如,在 Windows 上,您可以这样设置环境变量:

import os

os.environ["ORACLE_HOME"] = r"C:\oracle\instantclient_11_2"
os.environ["PATH"] = os.environ["ORACLE_HOME"] + os.pathsep + os.environ["PATH"]

将 C:\oracle\instantclient_11_2 替换为您的 Oracle 客户端库的实际路径。

最后,您可以在程序中检查可用的数据库驱动程序,以确保 QOCI 驱动程序可用。

要检查可用驱动程序,请使用 QSqlDatabase.drivers() 方法:

from PyQt5.QtSql import QSqlDatabase

available_drivers = QSqlDatabase.drivers()
print("Available drivers:", available_drivers)

如果 QOCI 驱动程序可用,它应该在输出的驱动程序列表中。

请按照这些步骤检查和解决驱动程序未加载的问题。

如果问题仍然存在,请提供有关您的系统配置和 Qt 安装的更多详细信息,以便我们可以更好地帮助您解决问题。

hejialiangya 发表于 2023-4-13 16:37:02

捣鼓了2天QSqlQuery和QSqlQueryModel的方法没有成功
最终还是退回到遍历填充单元格的办法。不过还是感谢isdkz大神的悉心指导。
页: [1]
查看完整版本: 嗨嗨嗨,又是我,新手又有问题出现,求大神帮忙