当前位置: 首页 > news >正文

Qt中使用MySQL数据库详解,好用的模块类封装

本文将详细介绍如何在Qt应用程序中集成MySQL数据库,并封装实现好用的mysql数据库操作类。包括环境准备、连接数据库、执行查询及异常处理等关键步骤,同时包含mysql驱动的编译。分享给有需要的小伙伴,喜欢的可以点击收藏。

目录

环境准备

项目配置

简单使用

 简单示例

模块类封装

 如何使用

附qsqlmysql库的构建

前提条件

构建步骤

1. 查找Qt的安装路径和编译器

2. 设置环境变量

3. 获取MySQL开发库

4. 构建 qsqlmysql 插件

Windows:

Linux:

5. 将编译好的插件拷贝到合适的位置

注意事项

其他资源


Qt提供了QtSql模块来进行独立于平台的数据库操作,这里的“平台”既包括操作系统平台,也包括各个数据库平台。Qt使用一个QDatabase表示一个数据库连接。在底层,Qt使用不同的驱动程序来与不同的数据库API进行交互。

通常Qt只默认搭载了QSqlLite驱动程序,如果需要使用其他数据库,需要下载相应的数据库驱动,如mysql的为 qsqlmysql.dll,同时还需要mysql的客户端库libmysql.dll。

在连接数据库之前可以使用QSqlDatabase::drivers()查看本机Qt已经支持的数据库驱动。

环境准备

1.安装MySQL数据库:首先确保你的系统中安装了MySQL服务器,并创建好数据库和表结构。

2.安装Qt开发环境:安装Qt Creator及Qt库,确保包含SQL驱动模块。

注意:Qt默认并不包括MySQL驱动,需要手动构建。在QT安装目录(如Qt5.12.11\5.12.11\msvc2015_64\plugins\sqldrivers)里找,是否有qsqlmysql.dll和qsqlmysqld.dll.

如果没有则需要基于QT源码从新构建,构建好后把qsqlmysql.dll放入plugins\sqldrivers目录中。如果不存在该库,则程序执行会报QSqlDatabase: QMYSQL driver not loaded的错误。

如果要构建QMYSQL,需安装Qt源代码,并确保你的系统中安装了MySQL服务器或至少安装了MySQL Connector/C++,因为构建过程需要MySQL的头文件和库文件。

可以通过以下方式查看支持哪些驱动:

 qDebug()<<"support drivers:"<<QSqlDatabase::drivers();

3.安装MySQL的c/c++的Connector(MySQL客户端库):对于Qt 5.12及以上版本,MySQL驱动可能已内置,但若缺失,需下载MySQL Connector/C++并安装,确保Qt能找到libmysql动态库。(libmysql.dll动态库。链接:MySQL :: Download MySQL Connector/C (Archived Versions))

将压缩包解压,将lib文件夹下的libmysql.dll和libmysql.lib文件拷贝到Qt的安装目录的bin文件夹下即可。 

项目配置

在你的Qt项目文件(.pro)中添加如下行以启用SQL模块:

QT += sql

简单使用

编写代码连接数据库:

#include <QSqlDatabase>
#include <QSqlQuery>
#include <QSqlError>
#include <QDebug>void connectToDatabase() {QSqlDatabase db = QSqlDatabase::addDatabase("QMYSQL");db.setHostName("localhost");db.setDatabaseName("testdb");db.setUserName("root");db.setPassword("password");if (!db.open()) {qDebug() << "Failed to connect to database:" << db.lastError().text();} else {qDebug() << "Connected to database!";}
}

 简单示例

#include <QCoreApplication>
#include <QSqlDatabase>
#include <QSqlQuery>
#include <QSqlError>
#include <QDebug>void connectToDatabase() {QSqlDatabase db = QSqlDatabase::addDatabase("QMYSQL");db.setHostName("localhost");db.setDatabaseName("testdb");db.setUserName("root");db.setPassword("password");if (!db.open()) {qDebug() << "Failed to connect to database:" << db.lastError().text();} else {qDebug() << "Connected to database!";}
}bool createTable() {QSqlQuery query;bool success = query.exec("CREATE TABLE person (id INT PRIMARY KEY, name VARCHAR(40))");if (!success) {qDebug() << "Failed to create table:" << query.lastError().text();}return success;
}bool insertRecord(int id, const QString &name) {QSqlQuery query;query.prepare("INSERT INTO person (id, name) VALUES (:id, :name)");query.bindValue(":id", id);query.bindValue(":name", name);bool success = query.exec();if (!success) {qDebug() << "Failed to insert record:" << query.lastError().text();}return success;
}void queryRecords() {QSqlQuery query("SELECT id, name FROM person");while (query.next()) {int id = query.value(0).toInt();QString name = query.value(1).toString();qDebug() << id << name;}
}int main(int argc, char *argv[])
{QCoreApplication a(argc, argv);connectToDatabase();createTable();insertRecord(1, "Alice");insertRecord(2, "Bob");queryRecords();return a.exec();
}

模块类封装

直接使用不太好用,这里做一个模块类封装,变得更好用啦,接口变得简单清晰。如果不封装,则原始是使用大概如下:

    QSqlQuery query(QSqlDatabase::database(connectionName, true));query.prepare("insert into test(name,age) values(:nameL,:ageL)");QStringList namelist;namelist<<"Tt"<<"Pp"<<"Kk";query.bindValue(":nameL",namelist);QVariantList agelist;agelist<<40<<50<<60;query.bindValue(":ageL",agelist);if(!query.execBatch()){qDebug()<<"数据插入失败: "<<query.lastError().text();}else{qDebug()<<"数据插入成功!";}

可以看到使用比较繁琐,封装后的模块代码如下: 

#include "mysqldb.h"
#include <QDebug>
#include <QUuid>mysqlDb::mysqlDb() {qDebug()<<"support drivers:"<<QSqlDatabase::drivers();
}mysqlDb::~mysqlDb() {disConnectSql();
}//打开连接
bool mysqlDb::connectSql(const QString &dbName) {mdbName_= dbName;db = QSqlDatabase::database(connectionName);if(!db.isValid()) {QUuid qUuid = QUuid::createUuid();QString strUuid = qUuid.toString();connectionName = QString("mysql-%1").arg(strUuid);db = QSqlDatabase::addDatabase("QMYSQL",connectionName);db.setHostName(mhost_); //根据实际情况设置主机名db.setPort(mport_);db.setDatabaseName(dbName);db.setUserName(muser_); //根据实际情况设置用户名db.setPassword(mpwd_); //根据实际情况设置密码db.setConnectOptions("MYSQL_OPT_RECONNECT=1"); // 支持断线重连if (!db.open()) {qWarning("Failed to open database: %s", qPrintable(db.lastError().text()));return false;}}return true;
}
//打开连接
bool mysqlDb::connectSql(const QString &host, int port, const QString &dbName, const QString &userName, const QString &password) {mhost_= host;mport_= port;mdbName_= dbName;muser_= userName;mpwd_ = password;db = QSqlDatabase::database(connectionName);if(!db.isValid()) {QUuid qUuid = QUuid::createUuid();QString strUuid = qUuid.toString();connectionName = QString("mysql-%1").arg(strUuid);db = QSqlDatabase::addDatabase("QMYSQL",connectionName);db.setHostName(host); //根据实际情况设置主机名db.setPort(port);db.setDatabaseName(dbName);db.setUserName(userName); //根据实际情况设置用户名db.setPassword(password); //根据实际情况设置密码db.setConnectOptions("MYSQL_OPT_RECONNECT=1"); // 支持断线重连if (!db.open()) {qWarning("Failed to open database: %s", qPrintable(db.lastError().text()));return false;}}return true;
}//关闭连接
bool mysqlDb::disConnectSql() {db = QSqlDatabase::database(connectionName);if(!db.isValid()) {return true;}db.close();QSqlDatabase::removeDatabase(connectionName);connectionName = "";return true;
}//错误打印
void mysqlDb::errorSql(QString sql) {errorSqlText = sql;qCritical("%s", qPrintable(errorSqlText));
}//获取错误的数据库语句
QString mysqlDb::getErrorSql() {if(connectionName.isEmpty()) {return "db not setting";}return errorSqlText;
}void mysqlDb::setMdbName(const QString &mdbName)
{mdbName_ = mdbName;
}void mysqlDb::setMpwd(const QString &mpwd)
{mpwd_ = mpwd;
}void mysqlDb::setMuser(const QString &muser)
{muser_ = muser;
}void mysqlDb::setMhost(const QString &mhost)
{mhost_ = mhost;
}void mysqlDb::setMport(int mport)
{mport_ = mport;
}//执行sql语句,不获取结果
bool mysqlDb::queryExec( QString queryStr) {if(connectionName.isEmpty()) {if(!connectSql(mhost_,mport_,mdbName_,muser_,mpwd_)) {return false;}}QSqlQuery query(QSqlDatabase::database(connectionName, true));if(!query.exec(queryStr)) {errorSql(queryStr);return false;}return true;
}//执行sql语句,并获取结果
bool mysqlDb::queryExec( QString queryStr, QList<QHash<QString, QString>> &data) {data.clear();if(connectionName.isEmpty()) {if(!connectSql(mhost_,mport_,mdbName_,muser_,mpwd_)) {return false;}}QSqlQuery query(QSqlDatabase::database(connectionName, true));if(!query.exec(queryStr)) {errorSql(queryStr);return false;}QSqlRecord rec = query.record();while(query.next()) {QHash<QString, QString> rowData;for(int i = 0; i < rec.count(); i++) {QVariant::Type ty = query.value(i).type();if(QVariant::Type::Date == ty) {QDate temp = query.value(i).toDate();rowData[rec.fieldName(i)] = temp.toString("yyyy-MM-dd");} else if(QVariant::Type::Time == ty) {QTime temp = query.value(i).toTime();rowData[rec.fieldName(i)] = temp.toString("hh:mm:ss");} else if(QVariant::Type::DateTime == ty) {QDateTime temp = query.value(i).toDateTime();rowData[rec.fieldName(i)] = temp.toString("yyyy-MM-dd hh:mm:ss");} else {rowData[rec.fieldName(i)] = query.value(i).toString();}}data.append(rowData);}return true;
}//获取数据
bool mysqlDb::getData(QString tableName, QHash<QString, QString> &data, QString sqlWhere) {data.clear();QList<QHash<QString, QString>> dataList;if(!getData(tableName, dataList, sqlWhere)) {return false;}if(dataList.count() > 0) {data = dataList[0];}return true;
}//获取数据
bool mysqlDb::getData( QString tableName, QList<QHash<QString, QString>> &data, QString sqlWhere) {QString queryStr = "select * from " + tableName;if(!sqlWhere.isEmpty()) {queryStr += " " + sqlWhere;}return queryExec(queryStr, data);
}//获取数据
bool mysqlDb::getData(QString tableName, QHash<QString, QString> columndata, QList<QHash<QString, QString>> &data, QString sqlWhere) {QString colunmStr;if(columndata.count() == 0) {colunmStr = "*";} else {QStringList keys = columndata.keys();for(auto key : keys) {QString column = QString("%1 AS %2").arg(key).arg(columndata[key]);if(!colunmStr.isEmpty()) {colunmStr += ",";}colunmStr += column;}}QString queryStr = QString("SELECT %1 FROM %2 %3").arg(colunmStr).arg(tableName).arg(sqlWhere);return queryExec(queryStr, data);
}//增加
bool mysqlDb::addData(QString tableName, QHash<QString, QString> data) {if(data.isEmpty()) {return false;}QString queryStr = "INSERT INTO " + tableName + " ";QString fieldStr = "(", valueStr = "VALUES(";QHash<QString, QString>::iterator it;for(it = data.begin(); it != data.end(); ++it) {fieldStr += it.key() + ",";valueStr += "'" + it.value() + "',";}fieldStr = fieldStr.left(fieldStr.length() - 1);valueStr = valueStr.left(valueStr.length() - 1);fieldStr += ")";valueStr += ")";queryStr += fieldStr + " " + valueStr;return queryExec(queryStr);
}//删除
bool mysqlDb::delData(QString tableName, QString sqlWhere) {QString queryStr = "DELETE FROM " + tableName;if(!sqlWhere.isEmpty()) {queryStr += " " + sqlWhere;}return queryExec(queryStr);
}//修改
bool mysqlDb::updateData( QString tableName, QHash<QString, QString> data, QString sqlWhere) {QString queryStr = "UPDATE " + tableName + " ";QHash<QString, QString>::iterator it;QString setStr = "SET ";for(it = data.begin(); it != data.end(); ++it) {setStr += it.key() + "='" + it.value() + "'";setStr += ",";}setStr = setStr.left(setStr.length() - 1);queryStr += setStr;if(!sqlWhere.isEmpty()) {queryStr += " " + sqlWhere;}return queryExec(queryStr);
}bool mysqlDb::transaction() {if(connectionName.isEmpty()) {return false;}return db.transaction();
}bool mysqlDb::commit() {if(connectionName.isEmpty()) {return false;}return db.commit();
}
#ifndef MYSQLDB_H
#define MYSQLDB_H#include <QDir>
#include <QDate>
#include <QDateTime>
#include <QFileInfo>
#include <QString>
#include <QTime>
#include <QSqlDatabase>
#include <QSqlRecord>
#include <QSqlQuery>
#include <QSqlError>
#include <QVariant>class mysqlDb
{
public:mysqlDb();~mysqlDb();
public:bool connectSql(const QString &dbName);//打开连接bool connectSql(const QString &host, int port, const QString &dbName, const QString &userName, const QString &password);//打开连接bool disConnectSql();//关闭连接bool queryExec(QString sqlStr);//执行sql语句,不获取结果bool queryExec(QString sqlStr,QList<QHash<QString,QString>> &data);//执行sql语句,并获取结果bool getData(QString tableName,QHash<QString,QString> &data,QString sqlWhere=""); //获取数据bool getData(QString table,QList<QHash<QString,QString>> &data,QString sqlWhere=""); //获取数据bool getData(QString tableName,QHash<QString,QString> columndata,QList<QHash<QString,QString>> &data,QString sqlWhere=""); //获取数据bool addData(QString tableName,QHash<QString,QString> data);//增加bool delData(QString tableName,QString sqlWhere);//删除bool updateData(QString tableName,QHash<QString,QString> data,QString sqlWhere="");//修改bool transaction();bool commit();QString getErrorSql();//获取错误的数据库语句void setMhost(const QString &mhost);void setMport(int mport);void setMdbName(const QString &mdbName);void setMuser(const QString &muser);void setMpwd(const QString &mpwd);private:QSqlDatabase db;QString connectionName="";QString errorSqlText;//错误语句QString mdbName_="";QString mhost_ = "localhost";int mport_ = 3306;QString muser_="";QString mpwd_="";private:void errorSql(QString sql);//错误打印
};#endif // MYSQLDB_H

 如何使用

void MainWindow::on_btn_test_clicked()
{mysqlDb* db = new mysqlDb();db->setMhost("111.178.126.10");db->setMuser("xxxxxx");db->setMpwd("xxxxxx");bool ret = db->openSql("test");if(ret){qDebug("connect ok");//插入数据QHash<QString, QString> user;user.insert("name","yang");user.insert("age","30");ret = db->addData("user",user);if(ret){qDebug("insert ok");}else{qDebug("insert error");}//读取数据QList<QHash<QString, QString>> data;ret = db->getData("user",data,"");if(ret){qDebug("get ok");for(auto d:data){qDebug(d["user"].toStdString().c_str());qDebug(d["age"].toStdString().c_str());}}else{qDebug("get error");}//更新QHash<QString, QString> update;update.insert("age","35");ret = db->updateData("user",update,"where age = 30");if(ret){qDebug("updateData ok");}else{qDebug("updateData error");}//删除ret = db->delData("user","where age = 32");if(ret){qDebug("delete ok");}else{qDebug("delete error");}}else{qDebug("connect error");}
}

附qsqlmysql库的构建

如果已经有该库,以下步骤可忽略。该库位置在Qt5.xx\5.xx\msvc20xx_\plugins\sqldrivers

qsqlmysql库是Qt框架中用于连接MySQL数据库的一个插件库。它是Qt SQL模块的一部分,专门设计用于提供对MySQL数据库的支持。

前提条件

  1. 安装Qt:确保你已经安装了Qt和Qt Creator。
  2. 安装MySQL客户端库
    • Windows环境下,可以直接下载 MySQL C API 开发包 (MySQL Connector/C)。
    • Linux环境,可通过包管理器安装(例如 sudo apt-get install libmysqlclient-dev)。
    • macOS环境,可通过Homebrew安装(例如 brew install mysql-client)。
  3. 下载QT相应版本的源码,比如我的是Qt5.14.2。下载地址:https://download.qt.io/

构建步骤

1. 查找Qt的安装路径和编译器
  • 确认你的Qt安装路径。例如:C:\Qt\5.x.x\mingwxx_32
  • 确认你使用的编译器,如 MinGW 或 MSVC,以及其路径。
  • QT的源码不用全解压,只需要qtbase这个文件夹下的全部内容。
2. 设置环境变量
  • 将Qt的编译工具(如qmake)添加到系统的PATH变量中。
3. 获取MySQL开发库
  • 确保你已经下载并解压了 MySQL Connector/C 用于 Windows 系统;在Linux和macOS系统上安装相应的开发库会自动设置好的路径。
4. 构建 qsqlmysql 插件

使用Qtcreator打开D:\Qt\qtbase\src\plugins\sqldrivers\mysql\mysql.pro工程文件。

打开工程后,会报错:Cannot read qtsqldrivers-config.pri: No such file or directory

接下来需要对mysql.pro文件和它上一级的qsqldriverbase.pri文件做出修改:

修改qsqldriverbase.pri

QT  = core core-private sql-private# For QMAKE_USE in the parent projects.
#注释到这个
#include($$shadowed($$PWD)/qtsqldrivers-config.pri)
#新增加这个
include(./configure.pri)PLUGIN_TYPE = sqldrivers
load(qt_plugin)DEFINES += QT_NO_CAST_TO_ASCII QT_NO_CAST_FROM_ASCII

修改 mysql.pro:

TARGET = qsqlmysqlHEADERS += $$PWD/qsql_mysql_p.h
SOURCES += $$PWD/qsql_mysql.cpp $$PWD/main.cpp#注释到这个
#QMAKE_USE += mysqlOTHER_FILES += mysql.jsonPLUGIN_CLASS_NAME = QMYSQLDriverPlugin
#以下为新增
#!!mysql的lib路径
LIBS += D:\Qt\mysql-connector-c-6.1.11-winx64/lib/libmysql.lib
#!!mysql的include路径
INCLUDEPATH += $$quote(D:\Qt\mysql-connector-c-6.1.11-winx64/include)
#!!mysql的include路径
DEPENDPATH += $$quote(D:\Qt\mysql-connector-c-6.1.11-winx64/include)include(../qsqldriverbase.pri)#!!设置编译好的qmysql.dll放置的目录
DESTDIR = ../mysql/mysqlDll
5. 将编译好的插件拷贝到合适的位置
  • 将编译得到的 qsqlmysql.dll(或 libqsqlmysql.so 或 libqsqlmysql.dylib)放到Qt的插件目录下。例如 C:\Qt\5.x.x\mingwxx_64\plugins\sqldrivers(Windows)或 /path/to/qt/plugins/sqldrivers(Linux和macOS)。

注意事项

  1. 版本匹配:请确保你的 MySQL 客户端库版本与 MySQL 服务器版本兼容,同时确保与 Qt 使用的编译器版本一致。
  2. 路径问题:在运行示例程序时,所有路径要使用绝对路径或将相关路径加入到环境变量中以确保 Qt 能够找到相应的库文件。
  3. 权限问题:在Linux和macOS环境下,可能需要使用sudo来执行某些命令以拥有足够的权限。

按照上述步骤,你应该能够成功构建并使用 qsqlmysql 插件来连接 MySQL 数据库。

最后,附上编译好的mysql驱动,含windows和mac版本的(5.14.2,5.15.2,6.5.3)

链接如下:

https://pan.baidu.com/s/1m15DbFuFTtXfEyqyOS2cew
提取码: 2o2s

其他资源

https://www.cnblogs.com/zhuchunlin/p/16485933.html

QT连接MYSQL(保姆级成功案例)_qt mysql-CSDN博客

QT学习之路——Qt QMySQL driver not loaded问题(笔记)_qsqldatabase: qmysql driver not loaded qsqldatabas-CSDN博客

MySQL :: Download MySQL Connector/C (Archived Versions)

QT加载mysql失败,重新构建mysql源文件_qt重新加载资源文件-CSDN博客

QT操作Mysql数据库_qt mysql-CSDN博客

https://www.cnblogs.com/flygreen/p/18029637

Qt连接mysql数据库_不能找到qtsqldrivers-config.pri-CSDN博客

Linux下Qt 5.15.2源码下载及编译_qt5 linux 源码下载-CSDN博客

qt creator mysql_qt creator with mysql-CSDN博客

编译qt5.15.2(mac/windows)的mysql驱动(附带编译好的文件)_macos编译qt5.15.2-CSDN博客

相关文章:

Qt中使用MySQL数据库详解,好用的模块类封装

本文将详细介绍如何在Qt应用程序中集成MySQL数据库&#xff0c;并封装实现好用的mysql数据库操作类。包括环境准备、连接数据库、执行查询及异常处理等关键步骤&#xff0c;同时包含mysql驱动的编译。分享给有需要的小伙伴&#xff0c;喜欢的可以点击收藏。 目录 环境准备 项…...

C语言实现 人生重生模拟器游戏

目录 实现一个简化版的人生重开模拟器 1.菜单函数 2.game函数 3.幼年时期&#xff08;even函数&#xff09; 4.壮年时期&#xff08;Juvenile函数&#xff09; 课余时间实现的小游戏 实现一个简化版的人生重开模拟器 1.菜单函数 void menu() {printf("---------------…...

C语言两个较大数字相加

C语言两个较大数字相加 思路分析 由于C语言中的基本数据类型&#xff08;如int、long等&#xff09;有固定的大小&#xff0c;无法直接处理非常大的数字&#xff08;如数百位的数字&#xff09;。因此&#xff0c;我们需要采用字符串或数组来表示大数字&#xff0c;并逐位进行…...

大数据面试题之Flume

目录 介绍下Flume Flume架构 Flume有哪些Source 说下Flume事务机制 介绍下Flume采集数据的原理&#xff1f;底层实现&#xff1f; Flume如何保证数据的可靠性 Flume传输数据时如何保证数据一致性&#xff08;可靠性&#xff09; Flume拦截器 如何监控消费型Flu…...

js文件的执行和变量初始化缓存

js文件和变量初始化 全局变量举例js文件加载 全局变量举例 import * as turf from "turf/turf"; import earcut from "earcut"; import * as THREE from "three"; import { TextGeometry } from "three/addons/geometries/TextGeometry.js…...

无法定位程序输入点Z9 qt assertPKcS0i于动态链接库F:\code\projects\06_algorithm\main.exe

解决方法&#xff1a; 这个报错&#xff0c;是因为程序在运行时没要找到所需的dll库&#xff0c;如果把这个程序方法中对应库的目录下执行&#xff0c;则可正常执行。即使将图中mingw_64\bin 环境变量上移到msvc2022_64\bin 之前也不可以。 最终的解决方法是在makefile中设置环…...

GoLand 2024 for Mac GO语言集成开发工具环境

Mac分享吧 文章目录 效果一、下载软件二、开始安装1、双击运行软件&#xff08;适合自己的M芯片版或Intel芯片版&#xff09;&#xff0c;将其从左侧拖入右侧文件夹中&#xff0c;等待安装完毕2、应用程序显示软件图标&#xff0c;表示安装成功3、打开访达&#xff0c;点击【文…...

Protocol Buffer 基础(c++)

本教程提供了使用协议缓冲区的基本介绍。通过逐步创建一个简单的示例应用程序&#xff0c;介绍以下内容&#xff1a; 1.在.proto文件中定义消息格式。 2.使用 protocol buffer 编译器。 3.使用c protocol buffer API来写入和读取消息。 一、问题描述 将要使用的示例是…...

上位机网络通讯

目录 一 设计原型 二 后台源码 一 设计原型 二 后台源码 using System; using System.Net.Sockets; using System.Text; using System.Threading.Tasks; using System.Windows.Forms;namespace 上位机网络通讯 {public partial class Form1 : Form{public Form1(){Initializ…...

转让5000万无区域能源公司要求和流程

国家局的公司&#xff0c;也就是无地域无区域性的公司名称。这样的公司是还可以继续注册的&#xff0c;但是想要拥有国家局无区域的名称就不是那么容易的了。总局的企业要求高&#xff0c;也是实力的体现。对字号有保护。所以有很多人都对无地域的名称一直情有独钟。现有一家名…...

WordPress Quiz Maker插件 SQL注入漏洞复现(CVE-2024-6028)

0x01 产品简介 WordPress Quiz Maker插件是一款功能强大的测验生成工具,旨在帮助用户轻松、快速地构建复杂的测验和考试。插件支持多种问题类型,包括单选框(MCQ)、复选框(MCQ)、下拉列表(MCQ)、文本、短文本、数字、日期等。还支持横幅(HTML)显示信息性消息、填空题…...

Swift中的二分查找:全面指南

Swift中的二分查找&#xff1a;全面指南 简介 二分查找是计算机科学中的经典算法&#xff0c;被广泛用于在已排序的数组中高效地搜索目标值。与线性查找逐个检查每个元素不同&#xff0c;二分查找不断将搜索区间减半&#xff0c;因此在处理大数据集时要快得多。 在这篇博客中…...

BUG TypeError: GPT2Model.forward() got an unexpected keyword argument ‘past’

TypeError: GPT2Model.forward() got an unexpected keyword argument past’ 环境 transformers 4.38.1详情 这是由于新版的transformers 对GPT2Model.forward() 参数进行了改变导致的错误。具体是past名称改为了 past_key_values 。 解决方法 找到错误语…...

解析Kotlin中的Lambda【笔记摘要】

先看实例&#xff1a; fun b(param: Int): String {return param.toString() }fun a(funParam: (Int) -> String): String {return funParam(1) }a(::b) val d ::b1.双冒号 ::method 到底是什么&#xff1f;答&#xff1a;一个指向和该函数具有相同功能的对象的引用 因为…...

rust单元测试顺序执行

前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到网站。 存在的问题 有时候&#xff0c;不同单元测试之间可能会竞争相同的资源&#xff0c;比如读写相同的文件。在这种情况下&#xff0c;如果…...

力扣-744. 寻找比目标字母大的最小字母

文章目录 力扣题目代码工程 力扣题目 给你一个字符数组 letters&#xff0c;该数组按非递减顺序排序&#xff0c;以及一个字符 target。letters 里至少有两个不同的字符。 返回 letters 中大于 target 的最小的字符。如果不存在这样的字符&#xff0c;则返回 letters 的第一个…...

一篇文章搞懂弹性云服务器和轻量云服务器的区别

前言 在众多的云服务器类型中&#xff0c;弹性云服务器和轻量云服务器因其各自的特点和优势&#xff0c;受到了广大用户的青睐。那么&#xff0c;这两者之间到底有哪些区别呢&#xff1f;本文将为您详细解析。 弹性云服务器&#xff1a;灵活多变的计算资源池 弹性云服务器&…...

横穿自动驾驶

如果有一条线&#xff0c;可以穿起来所有自动驾驶的核心模块&#xff0c;那么我感觉它就是最优化&#xff0c;选择优化变量、构造优化问题、求解优化问题&#xff0c;这几个步骤贯穿了自动驾驶的始终。 先从我的自身接触顺序写起。最开始做个一点深度学习&#xff0c;那还是20…...

为什么网上商店需要翻译成其他语言

网上商店不仅仅是一个可以买到商品的网站。它是一个完整的电子商务平台&#xff0c;为来自世界各地的用户提供购买所需物品的机会。但是&#xff0c;为了让这些用户舒适地使用网站&#xff0c;需要高质量的翻译和本地化。 本地化是指产品或服务适应特定文化或市场的过程。它包…...

【高考志愿】交通运输工程

目录 一、专业概述 二、课程设置 三、就业前景 四、报考注意 五、未来发展 六、交通运输工程专业排名 高考志愿选择交通运输工程专业&#xff0c;无疑是一个既具远见又富有挑战性的决定。这个专业以其综合性强、实用性高的特点&#xff0c;吸引了大批有志于投身交通事业的…...

【深度学习】【Lora训练3】StabelDiffusion,Lora训练过程,秋叶包,Linux,SDXL Lora训练

为了便于使用&#xff0c;构建一个docker镜像来使用秋叶包。2024年6月26日。 docker run -it --gpus all -v /ssd/xiedong:/datax --net host kevinchina/deeplearning:pytorch2.3.0-cuda12.1-cudnn8-devel-xformers bashgit clone --recurse-submodules https://github.com/A…...

ubuntu系统下如何安装python

在Ubuntu系统下安装Python&#xff0c;有多种方法可供选择。以下是两种常见的方法&#xff1a; 一、使用apt包管理器安装 安装步骤如下&#xff1a; 首先更新软件包列表 sudo apt update安装Python 3&#xff1a; 输入以下命令以安装Python 3&#xff08;Ubuntu的默认Pyth…...

邦芒攻略:职场中学会这五种管好情绪的方法

​​我们在公司里面在跟同事的一些往来&#xff0c;或者说是工作的一些合作当中。相信很多人都会有与周围的一些人发生过一些各种的争执&#xff0c;或者说是一些分歧。当然作为每一个职场的人来说&#xff0c;每天都是工作很累的&#xff0c;也是都很辛苦的&#xff0c;所以说…...

Linux各种命令——tac命令,more 命令, less命令,head命令,tail命令,file 命令, stat 命令

注意&#xff1a;tac命令是倒置输出文件内容 #### tac - **作用&#xff1a;倒叙访问文件内容** - 格式&#xff1a;tac 参数 文件名 - **例如&#xff1a;** **tac /etc/passwd** #### more 命令 - 作用&#xff1a;翻页查看文件内容&#xff0c;适合内容较多的文件查看…...

【Rust入门教程】hello world程序

文章目录 前言Hello World程序运行总结 前言 对于学习任何一种新的编程语言&#xff0c;我们都会从编写一个简单的Hello World程序开始。这是一个传统&#xff0c;也是一个开始。在这篇文章中&#xff0c;我们将一起学习如何在Rust中编写你的第一个程序&#xff1a;Hello Worl…...

激活函数、向前传播、损失函数、梯度下降

激活函数 作用&#xff1a;主要引入了非线性。从而能解决很复杂的非线性关系。能更好地处理现实世界的数据和任务。 向前传播 向前传播描述了&#xff0c;神经网络中&#xff0c;输入层到输出层的信号传播和处理过程。输入层将特征数据输入&#xff0c;加权求和&#xff0c;…...

three.js - MeshStandardMaterial(标准网格材质)- 金属贴图、粗糙贴图

金属贴图、粗糙贴图 金属贴图&#xff1a;metalnessMap 和 粗糙贴图&#xff1a;roughnessMap&#xff0c;是用于模拟物体表面属性的两种重要贴图技术&#xff0c;这两种贴图&#xff0c;通常与基于物理的渲染&#xff08;PBR&#xff09;材质&#xff08;如&#xff1a;MeshSt…...

算法-位图与底层运算逻辑

文章目录 1. 位图的理论基础2. 完整版位图实现3. 底层的运算逻辑-位运算 1. 位图的理论基础 首先我们要理解什么是位图, 位图的一些作用是什么 位图法就是bitmap的缩写。所谓bitmap&#xff0c;就是用每一位来存放某种状态&#xff0c;适用于大规模数据&#xff0c;但数据状态又…...

黑马点评-Redis的缓存击穿,缓存雪崩,缓存穿透,互斥锁,逻辑过期

文章目录 1.缓存穿透2.缓存雪崩3.缓存击穿3.1 互斥锁3.2 基于逻辑过期 1.缓存穿透 解决办法 写入NULL值到Redis缓存&#xff0c;以后就会命中Redis的控制缓存而不会出现请求直接打到数据库的问题&#xff01; 代码 2.缓存雪崩 这个概念很好理解&#xff0c;雪崩就是无数的…...

8624 多项式系数累加和

这个问题可以通过使用数学的导数规则来解决。对于一个多项式&#xff0c;它的导数可以通过将每一项的系数乘以它的指数&#xff0c;然后降低该项的指数来得到。这个过程可以重复M次来得到多项式的M阶导数。然后&#xff0c;我们可以简单地将所有项的系数相加来得到结果。 以下…...