QTableView输出保存为.csv或.txt

10

我为一个Qt GUI编写了下面的代码以在QTableView(面向模型)中查看查询输出。现在我想将此输出保存为.csv或.txt文件。有建议使用QTableWidget(面向项),但我想坚持使用基于模型的方法。

void MainWindow::on_pushButton_clicked()
{
db = QSqlDatabase::addDatabase("QOCI");
db.setHostName("host");
db.setDatabaseName("db");
db.setUserName("uid");
db.setPassword("pw");
db.setPort(port);

QString MyQuery = ui->lineEdit->text();

if (db.open())
{
    qDebug()<<QDateTime::currentDateTime()<<"QUERY DONE SUCCESSFULLY ";

    this->model=new QSqlQueryModel();
    model->setQuery(MyQuery);
    ui->tableView->setModel(model);

}
else
{
    qDebug()<<QDateTime::currentDateTime()<<"YOU FORGOT THE QUERY "<<db.lastError().text();
}

}

有任何指南吗?

3个回答

14

您可以根据实际需要进行自定义:

// [Collect model data to QString]
QString textData;
int rows = model->rowCount();
int columns = model->columnCount();

for (int i = 0; i < rows; i++) {
    for (int j = 0; j < columns; j++) {

            textData += model->data(model->index(i,j)).toString();
            textData += ", "      // for .csv file format
    }
    textData += "\n";             // (optional: for new line segmentation)
}

// [Save to file] (header file <QFile> needed)
// .csv
QFile csvFile("test.csv");    
if(csvFile.open(QIODevice::WriteOnly | QIODevice::Truncate)) {

    QTextStream out(&csvFile);
    out << textData;

    csvFile.close();
} 

// .txt
QFile txtFile("test.txt");    
if(txtFile.open(QIODevice::WriteOnly | QIODevice::Truncate)) {

    QTextStream out(&txtFile);
    out << textData;

    txtFile.close();
} 

1
反过来也可以吗?也就是说,使用这个 .csv 或 .txt 来填充 QTableView?如果有代码片段或文档链接将非常有帮助。再次感谢。 - RicoRicochet
1
@AmarjitBiswas 当然可以,但是无论是 .csv 还是 .txt 文件,您都必须“解析”文件。换句话说,您必须确定顺序数据(例如 .csv 文件)的映射方法,以将其与 QTableView 的数据模型对应。我建议您提出一个新问题并指定您的需求,因为反向方法需要您首先确定文件格式。否则,回答会太笼统。 - Tay2510
1
@AmarjitBiswas 嗯...我刚刚发现你在这里提出了一个类似的问题here,这会有什么影响吗? - Tay2510
1
其实,我之前的计划是直接导入到sqlite3数据库,但由于sqlite3的.dot命令无法直接集成到qt-c++中,所以我正在尝试遵循一个较长的过程。对于我的目的来说,执行速度并不重要,所以我打算使用.csv或.txt文件来保存检索到的数据副本,然后使用调度程序将它们加载到sqlite数据库中。 - RicoRicochet
1
我按建议在一个单独的问题中发布了我的疑问,链接为https://dev59.com/f4Xca4cB1Zd3GeqPOdt7,谢谢... - RicoRicochet
显示剩余2条评论

4

这里有一种使用qt将qtableview导出为csv的方法,包括列名。

   void staticmethods::exportTableViewToCSV(QTableView *table) {
            QString filters("CSV files (*.csv);;All files (*.*)");
            QString defaultFilter("CSV files (*.csv)");
            QString fileName = QFileDialog::getSaveFileName(0, "Save file", QCoreApplication::applicationDirPath(),
                               filters, &defaultFilter);
            QFile file(fileName);

            QAbstractItemModel *model =  table->model();
            if (file.open(QFile::WriteOnly | QFile::Truncate)) {
                QTextStream data(&file);
                QStringList strList;
                for (int i = 0; i < model->columnCount(); i++) {
                    if (model->headerData(i, Qt::Horizontal, Qt::DisplayRole).toString().length() > 0)
                        strList.append("\"" + model->headerData(i, Qt::Horizontal, Qt::DisplayRole).toString() + "\"");
                    else
                        strList.append("");
                }
                data << strList.join(";") << "\n";
                for (int i = 0; i < model->rowCount(); i++) {
                    strList.clear();
                    for (int j = 0; j < model->columnCount(); j++) {

                        if (model->data(model->index(i, j)).toString().length() > 0)
                            strList.append("\"" + model->data(model->index(i, j)).toString() + "\"");
                        else
                            strList.append("");
                    }
                    data << strList.join(";") + "\n";
                }
                file.close();
            }

        }

只需注意,尽管此调用将其输出命名为 .csv 文件,但它使用的分隔符是“;”... - Clare Macrae
输出的 CSV 文件将一行中的所有列合并到一个单元格中,但我期望的是每个列占用一个单元格,因此我通过将 data << strList.join(";") << "\n"; 替换为 data << strList.join(",") << "\n"; 来修改上面的代码。 - Wade Wang
我尝试使用这段代码导出一些来自串口的数据。它可以正常工作,但是所有数据都显示在第一行中。我该如何添加制表符以跳转到下一列?这里是我提出的问题,但我找不到解决方法。 - ysncck

4

您可以通过以下方式将模型保存到文本文件中:

QFile f( "table.txt" );
if( f.open( QIODevice::WriteOnly ) )
{
    QTextStream ts( &f );
    QStringList strList;
    for (int i=0; i<model->rowCount(); i++)
    {
        strList.clear();

        for (int j=0; j<model->columnCount(); j++)
            strList << model->data(model->index(i,j)).toString();

        ts << strList.join(" ") + "\n";
    }
    f.close();
}

在这里,模型数据以每行一个空格的方式保存。如果您想用逗号等其他字符分隔它们,只需更改连接参数上的参数即可:

ts << strList.join(",") + "\n";

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接