目录
1.QTableView简介
2.QTableWidget简介
3.QTableView和QTableWidget不同
4.总结
1.QTableView简介
QTableView是一个基于模型-视图架构的表格控件,用于展示表格形式的数据。同样需要关联一个QAbstractTableModel或其子类(如QStandardItemModel)来提供数据。这意味着数据存储在模型中,而 QTableView 只负责显示和编辑这些数据。它将数据显示与数据存储分离,提供了强大的灵活性和可扩展性,适合处理各种复杂的表格场景。
它在QT中的类继承关系如下图所示:
它的特点有:
1)高性能:采用懒加载机制,仅渲染可见区域的单元格,适合处理大量数据(如数万行以上)。
2)高度可定制化:
- 支持自定义单元格渲染(通过
QAbstractItemDelegate
)。 - 可定制行高、列宽、排序、筛选等功能。
- 通过样式表(CSS)修改整体外观。
可自定义单元格的渲染和编辑方式,例如显示进度条、下拉框等:
class ProgressDelegate : public QItemDelegate {
public:void paint(QPainter *painter, const QStyleOptionViewItem &option,const QModelIndex &index) const override {// 绘制进度条int progress = index.data().toInt();QStyleOptionProgressBar progressBar;// ... 设置进度条参数QApplication::style()->drawControl(QStyle::CE_ProgressBar, &progressBar, painter);}
};// 使用代理
tableView.setItemDelegateForColumn(2, new ProgressDelegate);
排序与筛选
// 启用排序
tableView.setSortingEnabled(true);// 使用筛选器(如只显示年龄>20的行)
QSortFilterProxyModel proxyModel;
proxyModel.setSourceModel(&originalModel);
proxyModel.setFilterRegExp("^[2-9][0-9]$");
proxyModel.setFilterKeyColumn(1); // 筛选第2列(年龄)
tableView.setModel(&proxyModel);
3)丰富的交互支持:支持单元格选择、编辑、右键菜单、拖放等操作,并提供相应信号(如 clicked
、doubleClicked
)。
4)数据库集成:通过 QSqlTableModel
直接连接数据库表:
#include <QSqlTableModel>
QSqlTableModel model;
model.setTable("employees");
model.select(); // 查询数据
tableView.setModel(&model);
2.QTableWidget简介
QTableWidget继承于QTableView,它是一个结合了模型和视图的控件,它内置了一个简单的表格模型。这意味着你不需要单独管理模型,可以直接通过QTableWidget的方法来操作数据。与 QTableView
相比,QTableWidget
的 API 更简单直接,适合快速开发小规模、静态数据的表格应用。
它的特点有:
1)集成数据存储:无需额外的数据模型(如 QStandardItemModel
),可直接通过 setItem()
、setCellWidget()
操作单元格数据。
2)简单易用:提供直观的 API,适合初学者快速实现表格功能,例如:
QTableWidget table(4, 2); // 创建4行2列的表格
table.setItem(0, 0, new QTableWidgetItem("张三"));
3)基本功能齐全: 支持单元格选择、编辑、排序、行 / 列隐藏等常见操作。
4)视觉定制:可通过样式表(CSS)修改外观,或通过 setCellWidget()
添加自定义控件(如按钮、下拉框)。
3.QTableView和QTableWidget不同
特性 | QTableView | QTableWidget |
---|---|---|
数据模型 | 基于 MVC(模型 - 视图 - 控制器)架构,需配合QAbstractItemModel 子类(如QStandardItemModel 、QSqlTableModel )使用。数据与视图分离,支持大型数据集。 | 内置数据存储(直接操作单元格),无需额外模型。适合小规模静态数据。 |
使用复杂度 | 需手动创建和配置模型,学习成本较高,但灵活性极强。 | 开箱即用,API 简单直接,适合快速开发。 |
性能 | 处理大量数据时性能更佳(如数万行以上),仅渲染可见区域。 | 数据量较大时性能下降,因所有单元格预分配。 |
扩展性 | 可自定义模型实现高级功能(如异步加载、远程数据)。 | 扩展困难,需继承并重写大量方法。 |
单元格操作 | 通过模型间接操作数据(如model.setData(index, value) )。 | 直接通过setItem() 、setCellWidget() 操作单元格。 |
典型应用场景
-
QTableView:
- 数据量庞大(如数据库查询结果)。
- 需要与其他组件共享数据模型。
- 需要自定义数据展示逻辑(如图标、富文本、进度条)。
-
QTableWidget:
- 数据量较小且固定。
- 快速原型开发或简单表格需求。
- 直接操作单元格内容(如 Excel 式编辑)。
示例代码:QTableView + QStandardItemModel(C++)
#include <QApplication>
#include <QTableView>
#include <QStandardItemModel>int main(int argc, char *argv[]) {QApplication a(argc, argv);// 创建模型QStandardItemModel model(4, 2); // 4行2列model.setHorizontalHeaderLabels({"姓名", "年龄"});// 设置数据model.setItem(0, 0, new QStandardItem("张三"));model.setItem(0, 1, new QStandardItem("25"));// 创建视图并设置模型QTableView tableView;tableView.setModel(&model);tableView.show();return a.exec();
}
QTableWidget(C++)
#include <QApplication>
#include <QTableWidget>
#include <QTableWidgetItem>int main(int argc, char *argv[]) {QApplication a(argc, argv);// 创建表格,设置行列数QTableWidget tableWidget(4, 2);tableWidget.setHorizontalHeaderLabels({"姓名", "年龄"});// 设置数据tableWidget.setItem(0, 0, new QTableWidgetItem("张三"));tableWidget.setItem(0, 1, new QTableWidgetItem("25"));tableWidget.show();return a.exec();
}
4.总结
- 选 QTableView:当需要处理复杂数据逻辑或大量数据时,它提供更好的性能和可维护性。
- 选 QTableWidget:当需求简单且数据量较小时,它能快速实现功能。
实际开发中,建议优先使用QTableView
,因为 MVC 架构更符合软件工程原则,便于代码扩展和维护。