Qt C++ TCP服务端响应多客户端通讯

本示例使用的设备:WIFI无线4G网络RFID云读卡器远程网络开关物流网阅读器TTS语音-淘宝网 (taobao.com)

#include "mainwindow.h"
#include "ui_mainwindow.h"
#include "QMessageBox"
#include <QDebug>
#include <exception>
#include <QTcpServer>
#include <QTcpSocket>
#include <QObject>
#include <QTime>
#include <QTreeWidgetItem>
#include <QClipboard>

bool listening=false;
QTcpServer m_server;
QTcpSocket m_socket;

//获取本机所有网卡IP------------------------------------------------------------------------------------------------------
QStringList getAllIPAddresses() {
    QStringList ips;
    QList<QHostAddress> list = QNetworkInterface::allAddresses();
    for (int i = 0; i < list.size(); ++i) {
        QHostAddress address = list.at(i);
        // 检查是否为IPv4地址,并排除回环地址
        if (address.protocol() == QAbstractSocket::IPv4Protocol && address != QHostAddress::LocalHost) {
            ips << address.toString();
        }
    }
    return ips;
}

//获取系统现时间-------------------------------------------------------------------------------------------------------------
QString getsystime(){
    QTime time = QTime::currentTime();
    QString timeStr = time.toString("hh:mm:ss.zzz");
    return timeStr;
}

//获取系统日期时间-------------------------------------------------------------------------------------------------------------
QString getsysdatetime(){
    QDateTime currentDateTime = QDateTime::currentDateTime();
    QString dateTimeString = currentDateTime.toString("yy-MM-dd hh:mm:ss");
    return dateTimeString;
}

//QByteArray转16进制QString------------------------------------------------------------------------------------------------
QString ByteArrayToHexString(QByteArray data){
    QString ret(data.toHex().toUpper());
    int len = ret.length()/2;
    for(int i=1;i<len;i++)
    {
        ret.insert(2*i+i-1," ");
    }
    return ret;
}

//通讯报文显示-----------------------------------------------------------------------------------------------------
void MainWindow::listadditems(int ctr,QString listinfo){
    switch (ctr){
    case 0:
        if(ui->listWidget_report->count()>30){
            ui->listWidget_report->clear();
        }
        ui->listWidget_report->addItem(listinfo);
        ui->listWidget_report->setCurrentRow(ui->listWidget_report->count()-1);
        break;
    case 1:
        ui->listWidget_online->addItem(listinfo);
        ui->listWidget_online->setCurrentRow(ui->listWidget_online->count()-1);
    }
}


MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent)
    , ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    ui->TEPort->setPlainText("39169");        //出厂默认39169端口
    ui->spinBox_dispdelay->setValue(20);
    ui->spinBox_swit->setValue(30);
    ui->spinBox_voice->setValue(8);
    ui->textEdit_disp->setText("欢迎您使用我们的网络读卡器!");
    ui->textEdit_tts->setText("感谢您的使用,您的支持是我们最大的动力!");

    QStringList ips = getAllIPAddresses();
    foreach (QString ip, ips) {
        ui->CBIP->addItem(ip);
    }
    if(ui->CBIP->count()<1){
        QMessageBox::information(NULL, "提示", "未搜索到本机的网卡,系统不能正常运行!");
        delete ui;
    }
}

MainWindow::~MainWindow()
{
    delete ui;
}

//启动、关闭TCP服务-------------------------------------------------------------------------------------------------------
void MainWindow::initserver(){
    try{
        if(ui->pushButton_initserver->text()=="开启TCP服务"){
            QString ipstr=ui->CBIP->currentText();
            QHostAddress localeip(ipstr);
            quint16 port=ui->TEPort->toPlainText().toUInt();

            m_server = new QTcpServer(this);
            m_server->listen(localeip, port);
            connect(m_server, &QTcpServer::newConnection, this, &MainWindow::onNewConnection);

            listening=true;
            ui->pushButton_initserver->setText("停止");
            listadditems(0,getsystime()+" Tcp Server is listening...");
        }else{
            listening=false;
            m_server->close();
            ui->pushButton_initserver->setText("开启TCP服务");
            for(int i=0;i<tcpclientlist.count();i++){
                tcpclientlist.at(i)->close();
                //tcpclientlist.remove(i);
                ui->listWidget_online->takeItem(i);
            }
            tcpclientlist.clear();
            listadditems(0,getsystime()+" Tcp Server is close! ");
        }
    }
    catch(_exception)
    {
        listening=false;
        ui->pushButton_initserver->setText("开启TCP服务");
    }
}

//侦听到有新的TCP客户端接入服务--------------------------------------------------------------------------------------------
void MainWindow::onNewConnection()
{
    m_socket = m_server->nextPendingConnection();
    tcpclientlist.append(m_socket);

    QString RemoIp=m_socket->peerAddress().toString();
    QString RemoPort=QString::number( m_socket->peerPort());
    listadditems(1,RemoIp+":"+RemoPort);
    listadditems(0,getsystime()+" NewConn "+RemoIp+":"+RemoPort);

    connect(m_socket, &QTcpSocket::readyRead, this, &MainWindow::onReadyRead);
    connect(m_socket, &QTcpSocket::disconnected, this, &MainWindow::onClientDisconnected);
    connect(m_socket, &QTcpSocket::connected, this, &MainWindow::onConnected);
//  connect(m_socket, &QTcpSocket::stateChanged, this, &MainWindow::onStateChanged);

}


//接收到TCP客户端传送来来的数据-------------------------------------------------------------------------------------------
void MainWindow::onReadyRead()
{
    QByteArray buffer;
    for(int row=0;row<tcpclientlist.count();row++){
        m_socket=tcpclientlist.at(row);
        buffer = m_socket->readAll();
        if(buffer.length()!=0){
            QString RemoIp=m_socket->peerAddress().toString();
            QString RemoPort=QString::number( m_socket->peerPort());
            listadditems(0,getsystime()+" Receive: "+RemoIp+":"+RemoPort+"    "+ByteArrayToHexString(buffer));

            unsigned char databuff[buffer.length()];
            std::copy(buffer.begin(), buffer.end(), databuff);

            switch (databuff[0]){
            case 0xc1:
            case 0xcf:
                 Analyze_c1_cf(row,databuff,buffer.length());          //解析读取IC卡卡号
                 break;

            case 0xd1:
            case 0xdf:
                 Analyze_d1_df(row,databuff,buffer.length());          //解析读取ID卡卡号
                 break;

            default:
                break;
            }
        }
    }
}


//侦测到TCP客户端断开连接---------------------------------------------------------------------------------------------
void MainWindow::onClientDisconnected()
{
    QString RemoIp=m_socket->peerAddress().toString();
    quint16 RemoPort= m_socket->peerPort();
    for(int i=0;i<tcpclientlist.count();i++){
        if(tcpclientlist.at(i)->peerAddress().toString()==RemoIp && tcpclientlist.at(i)->peerPort()==RemoPort){
            tcpclientlist.remove(i);
            ui->listWidget_online->takeItem(i);
            listadditems(0,getsystime()+" Disconn: "+RemoIp+":"+QString::number(RemoPort));
        }
    }
}


void MainWindow::onConnected()
{
    QString RemoIp=m_socket->peerAddress().toString();
    QString RemoPort=QString::number( m_socket->peerPort());
}

//void MainWindow::onStateChanged(QAbstractsocket::SocketState socketstate){
//    switch (socketstate){
//    case QAbstractSocket::UnconnectedState:ui->labConnectState->setText("Unconnectedstate");break;
//    case QAbstractSocket::HostLookupState:ui->labConnectState->setText("HostLookupstate");break;
//    case QAbstractSocket::ConnectedState:ui->labConnectState->setText("connectedstate");break;
//    case QAbstractSocket::ConnectingState:ui->labConnectState->setText("connectingstate");break;
//    case QAbstractSocket::BoundState: ui->labConnectState->setText("Boundstate");break;
//    case QAbstractSocket::ClosingState:ui->labConnectState->setText("closingstate");break;
//    case QAbstractSocket::ListeningState:ui->labConnectState->setText("listeningstate");break;
//    }
//}


//解析读取IC卡卡号-------------------------------------------------------------------------------------------------------------------
void MainWindow::Analyze_c1_cf(int socketid,unsigned char databuff[], qint64 buflen)
{
    QString IPAddress=QString::asprintf("%d", databuff[1])+"."+QString::asprintf("%d", databuff[2])+"."+QString::asprintf("%d", databuff[3])+"."+QString::asprintf("%d", databuff[4]); //设备IP地址,广域网上使用,一般不对此IP回应,而是对数据流的 ip及端口 回应
    QString DeviceNumber=QString::asprintf("%05d",databuff[5]+databuff[6]*256);   //设备自编机号
    QString FrameNumber=QString::asprintf("%05d",databuff[7]+databuff[8]*256);    //数据包号
    int cardnolen=databuff[9];

    QString CardnoHexZ="";          //16进制卡号正码
    QString CardnoHexF="";          //16进制卡号反码
    for (int i=0;i<cardnolen;i++){
        CardnoHexZ=CardnoHexZ+QString::asprintf("%02X", databuff[10+i]);
        if(i<4){CardnoHexF=CardnoHexF+QString::asprintf("%02X", databuff[9+cardnolen-i]);}   //只取4个字节计算8H10D反码
    }

    QString SerialNumber="";        //设备全球唯一硬件序号
    for (int i=10+cardnolen;i<buflen;i++){
        SerialNumber=SerialNumber+QString::asprintf("%02X", databuff[i]);
    }

    bool status;
    QString Cardno8H10D=QString::asprintf("%010u",CardnoHexF.toUInt(&status,16));  //转8H10D反码卡号

    QString  DispInf;
    if (databuff[0]==0xc1){DispInf="读取IC卡号,";}else{DispInf="IC卡离开读卡器,";}
    DispInf=DispInf+"设备IP:"+IPAddress+",机号:"+DeviceNumber+",数据包号:"+FrameNumber+",16进制卡号:"+CardnoHexZ+",转8H10D反码:"+Cardno8H10D+",设备全球唯一序号:"+SerialNumber;
    ui->plainTextEdit_msg->setPlainText(DispInf);

    if(ui->checkBox_Resp->isChecked()){Respondinfo(socketid,getsysdatetime()+"卡号:"+Cardno8H10D);}  //回应驱动设备显示+蜂鸣响声
}

//解析读取ID卡卡号-------------------------------------------------------------------------------------------------------------------
void MainWindow::Analyze_d1_df(int socketid,unsigned char databuff[], qint64 buflen)
{
    QString IPAddress=QString::asprintf("%d", databuff[1])+"."+QString::asprintf("%d", databuff[2])+"."+QString::asprintf("%d", databuff[3])+"."+QString::asprintf("%d", databuff[4]); //设备IP地址,广域网上使用,一般不对此IP回应,而是对数据流的 ip及端口 回应
    QString DeviceNumber=QString::asprintf("%05d",databuff[5]+databuff[6]*256);   //设备自编机号
    QString FrameNumber=QString::asprintf("%05d",databuff[7]+databuff[8]*256);    //数据包号

    QString CardnoHexZ="";          //16进制卡号正码
    QString CardnoHexF="";          //16进制卡号反码
    for (int i=0;i<5;i++){
        CardnoHexZ=CardnoHexZ+QString::asprintf("%02X", databuff[9+i]);
        if(i<4){CardnoHexF=CardnoHexF+QString::asprintf("%02X", databuff[9+3-i]);}   //只取4个字节计算8H10D反码
    }

    QString SerialNumber="";        //设备全球唯一硬件序号
    for (int i=9+5;i<buflen;i++){
        SerialNumber=SerialNumber+QString::asprintf("%02X", databuff[i]);
    }

    bool status;
    QString Cardno8H10D=QString::asprintf("%010u",CardnoHexF.toUInt(&status,16));  //转8H10D反码卡号

    QString  DispInf;
    if (databuff[0]==0xd1){DispInf="读取ID卡号,";}else{DispInf="ID卡离开读卡器,";}
    DispInf=DispInf+"设备IP:"+IPAddress+",机号:"+DeviceNumber+",数据包号:"+FrameNumber+",16进制卡号:"+CardnoHexZ+",转8H10D反码:"+Cardno8H10D+",设备全球唯一序号:"+SerialNumber;
                                                                                                                                                                          ui->plainTextEdit_msg->setPlainText(DispInf);

    if(ui->checkBox_Resp->isChecked()){Respondinfo(socketid,getsysdatetime()+"卡号:"+Cardno8H10D);}  //回应驱动设备显示+蜂鸣响声
}


void MainWindow::on_btnClose_clicked()
{
    m_server->close();
}


//向指定的客户端发送数据--------------------------------------------------------------------------------------------------------------
void MainWindow::SendBufToSockID(int socketid,QByteArray rbuffer){
    m_socket=tcpclientlist.at(socketid);
    m_socket->write(rbuffer);

    QString RemoIp=m_socket->peerAddress().toString();
    QString RemoPort=QString::number( m_socket->peerPort());
    QString SendHex=getsystime()+" Send To: "+(RemoIp+":"+RemoPort+"             ").mid(0,22);
    SendHex=SendHex+ByteArrayToHexString(rbuffer);
    listadditems(0,SendHex);
}


void MainWindow::on_pushButton_initserver_clicked()
{
    initserver();
}


//驱动读卡器蜂鸣响声-----------------------------------------------------------------------
void MainWindow::on_btnSendbeep_clicked()
{
    QListWidgetItem *item = ui->listWidget_online->currentItem();
    int row = ui->listWidget_online->row(item);
    if(row<0){
        QMessageBox::critical(this, "警告", "请选择一台在线设备再执行此功能!", QMessageBox::Ok);
    }else{
        QByteArray sendData;
        sendData.append(0x96);                             //功能码
        quint16 devno=0;
        sendData.append(devno % 256);                      //机号低位
        sendData.append(devno / 256);                      //机号高位,高低位都为0表示任意机号
        sendData.append(ui->CBbeep->currentIndex());       //蜂鸣响声代码
        SendBufToSockID(row,sendData);
    }
}

//驱动读卡器开启继电器-----------------------------------------------------------------------
void MainWindow::on_btnswitchon_clicked()
{
    QListWidgetItem *item = ui->listWidget_online->currentItem();
    int row = ui->listWidget_online->row(item);
    if(row<0){
        QMessageBox::critical(this, "警告", "请选择一台在线设备再执行此功能!", QMessageBox::Ok);
    }else{
        QByteArray sendData;
        sendData.append(0x78);                             //功能码
        quint16 devno=0;
        sendData.append(devno % 256);                      //机号低位
        sendData.append(devno / 256);                      //机号高位,高低位都为0表示任意机号
        QString swithno="F"+QString::asprintf("%d",ui->CBSwitch->currentIndex());
        bool status;
        sendData.append(swithno.toUInt(&status,16));       //选择继电器
        quint16 deltime=ui->spinBox_swit->value();
        sendData.append(deltime % 256);                    //开启延时低位
        sendData.append(deltime / 256);                    //开启延时高位
        SendBufToSockID(row,sendData);
    }
}

//驱动读卡器关闭已开启的继电器-----------------------------------------------------------------
void MainWindow::on_btnswitchoff_clicked()
{
    QListWidgetItem *item = ui->listWidget_online->currentItem();
    int row = ui->listWidget_online->row(item);
    if(row<0){
        QMessageBox::critical(this, "警告", "请选择一台在线设备再执行此功能!", QMessageBox::Ok);
    }else{
        QByteArray sendData;
        sendData.append(0x78);                             //功能码
        quint16 devno=0;
        sendData.append(devno % 256);                      //机号低位
        sendData.append(devno / 256);                      //机号高位,高低位都为0表示任意机号
        QString swithno="E"+QString::asprintf("%d",ui->CBSwitch->currentIndex());
        bool status;
        sendData.append(swithno.toUInt(&status,16));       //选择继电器
        quint16 deltime=ui->spinBox_swit->value();
        sendData.append(deltime % 256);                    //开启延时低位
        sendData.append(deltime / 256);                    //开启延时高位
        SendBufToSockID(row,sendData);
    }
}

//驱动读卡器蜂鸣响声并显示文字---------------------------------------------------------------------
void MainWindow::on_btnDispbeep_clicked()
{
    QListWidgetItem *item = ui->listWidget_online->currentItem();
    int row = ui->listWidget_online->row(item);
    if(row<0){
        QMessageBox::critical(this, "警告", "请选择一台在线设备再执行此功能!", QMessageBox::Ok);
    }else{
        QByteArray sendData;
        sendData.append(0x5A);                             //功能码
        quint16 devno=0;
        sendData.append(devno % 256);                      //机号低位
        sendData.append(devno / 256);                      //机号高位,高低位都为0表示任意机号
        sendData.append(ui->CBbeep->currentIndex());       //蜂鸣响声代码,255表示不响声
        sendData.append(ui->spinBox_dispdelay->value());   //文字显示时长,
        QString dispstr=ui->textEdit_disp->toPlainText()+"                                  ";  //加空格是为了确保满屏34位显示
        QByteArray Dispbyte=dispstr.toLocal8Bit();
        for(int i=0;i<34;i++){
            sendData.append(Dispbyte[i]);
        }
        SendBufToSockID(row,sendData);
    }
}

//驱动读卡器蜂鸣响声+显示文字+播报TTS语音+开启继电器开关
void MainWindow::on_btndispbeeptts_clicked()
{
    QListWidgetItem *item = ui->listWidget_online->currentItem();
    int row = ui->listWidget_online->row(item);
    if(row<0){
        QMessageBox::critical(this, "警告", "请选择一台在线设备再执行此功能!", QMessageBox::Ok);
    }else{
        if(ui->spinBox_voice->value()>16){ui->spinBox_voice->setValue(16);} //tts最大语音取值16
        QString strls="[v"+QString::asprintf("%d",ui->spinBox_voice->value())+"]";
        strls=strls+ui->textEdit_tts->toPlainText().trimmed();
        QByteArray SpeakArr=strls.toLocal8Bit();         //TS语音转换为Ansi码
        quint8 speakbytes=SpeakArr.size();
        quint8 dispbytes=34;                //双行显示屏显示长度34,四行屏显示长度72

        QByteArray sendData;
        sendData.append(0x5c);                             //功能码
        quint16 devno=0;
        sendData.append(devno % 256);                      //机号低位
        sendData.append(devno / 256);                      //机号高位,高低位都为0表示所有机
        sendData.append(ui->CBbeep->currentIndex());       //蜂鸣响声代码,取值255表示不响

        QString swithno="F"+QString::asprintf("%d",ui->CBSwitch->currentIndex());
        bool status;
        sendData.append(swithno.toUInt(&status,16));       //选择继电器
        quint16 deltime=ui->spinBox_swit->value();
        sendData.append(deltime % 256);                    //延时低位
        sendData.append(deltime / 256);                    //延时高位

        sendData.append(ui->spinBox_dispdelay->value());   //文字显示时长,
        quint8 begindisp =0;                               //在显示屏中的哪个位置开始显示,一般取0
        sendData.append(begindisp);
        sendData.append(dispbytes);                        //显示文字长度
        sendData.append(speakbytes);                       //tts语音长茺

        QString dispstr=ui->textEdit_disp->toPlainText()+"                                  ";  //加空格是为了确保满屏34位显示
        QByteArray Dispbyte=dispstr.toLocal8Bit();
        for(int i=0;i<dispbytes;i++){
            sendData.append(Dispbyte[i]);       //显示信息
        }
        for(int i=0;i<speakbytes;i++){
            sendData.append(SpeakArr[i]);       //TTS语音信息
        }

        sendData.append(0x55);      //防干扰后缀
        sendData.append(0xaa);
        sendData.append(0x66);
        sendData.append(0x99);
        SendBufToSockID(row,sendData);
    }
}

//接收到刷卡数据立即回应--------------------------------------------------------------------------
void MainWindow::Respondinfo(int socketid,QString Dispinf)
{
    QByteArray RespBuff;
    RespBuff.append(0x5A);                             //功能码
    quint16 devno=0;
    RespBuff.append(devno % 256);                      //机号低位
    RespBuff.append(devno / 256);                      //机号高位,高低位都为0表示任意机
    RespBuff.append(ui->CBbeep->currentIndex());       //蜂鸣响声代码,255表示不响声
    RespBuff.append(ui->spinBox_dispdelay->value());   //文字显示时长,
    QString dispstr=Dispinf+"                                  ";  //加空格是为了确保满屏34位显示
    QByteArray Dispbyte=dispstr.toLocal8Bit();
    for(int i=0;i<34;i++){
        RespBuff.append(Dispbyte[i]);
    }

    m_socket=tcpclientlist.at(socketid);
    m_socket->write(RespBuff);

    QString RemoIp=m_socket->peerAddress().toString();
    QString RemoPort=QString::number( m_socket->peerPort());
    QString SendHex=getsystime()+" Send To: "+(RemoIp+":"+RemoPort+"             ").mid(0,22);
    SendHex=SendHex+ByteArrayToHexString(RespBuff);
    listadditems(0,SendHex);
}


void MainWindow::on_btncopyreport_clicked()
{
    QString listinf;
    int row=ui->listWidget_report->count();
    if (row<1){
        return;
    }else{
        for (int i=0;i<row;i++){
            QListWidgetItem *item = ui->listWidget_report->item(i);
            listinf=listinf+item->text()+"\n";
        }
        QClipboard *clipboard = QApplication::clipboard();
        clipboard->setText(listinf);
        QMessageBox::information(this, "提示", "显示数据报文已拷贝到剪切板");
    }
}

源码下载 :https://download.csdn.net/download/zhangjin7422/89421064

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/711514.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Guitar Pro8 最新详细安装步骤 及解析

随着音乐文化的普及和发展&#xff0c;越来越多的人开始关注和学习吉他。而在吉他学习的道路上&#xff0c;一款优质的吉他软件无疑会给我们带来极大的便利和帮助。今天&#xff0c;我们就来探讨一款备受好评的吉他软件——Guita Pro8&#xff0c;看看它究竟有何魅力之处。 Gu…

NettyのNIOBIO原理解析

1、IO模型 在IO模型中&#xff0c;主要可分为同步与异步操作&#xff1a; 在同步 I/O 模型中&#xff0c;I/O 操作是阻塞的&#xff0c;当一个进程或线程执行 I/O 操作时&#xff0c;它会一直等待这个操作完成才继续执行后续的代码。 在异步 I/O 模型中&#xff0c;I/O 操作是非…

Google Earth Engine(GEE)——在控制台上答应出一个button按钮

函数: ui.Button(label, onClick, disabled, style) A clickable button with a text label. Arguments: label (String, optional): The buttons label. Defaults to an empty string. onClick (Function, optional): A callback fired when the button is clicked. T…

栈的实现详解

目录 1. 栈1.1 栈的概念及结构1.2 栈的实现方式1.3 栈的应用场景 2. 栈的实现2.1 结构体2.2 初始化2.3 销毁2.4 入栈2.5 出栈2.6 获取栈顶元素2.7 判空2.8 获取个数 3. test主函数4. Stack.c文件5. Stack.h文件6. 运行展示 1. 栈 1.1 栈的概念及结构 栈&#xff1a;一种特殊的…

2024.6.14 作业 xyt

使用手动连接&#xff0c;将登录框中的取消按钮使用第二中连接方式&#xff0c;右击转到槽&#xff0c;在该槽函数中&#xff0c;调用关闭函数 将登录按钮使用qt4版本的连接到自定义的槽函数中&#xff0c;在槽函数中判断ui界面上输入的账号是否为"admin"&#xff0c…

AI Agent智能应用从0到1定制开发(完结)

在数字化时代的浪潮中&#xff0c;人工智能&#xff08;AI&#xff09;代理智能应用如同星辰般璀璨&#xff0c;引领着技术革新的潮流。从零开始定制开发一款AI Agent智能应用&#xff0c;就像是在无垠的宇宙中绘制一颗新星的轨迹&#xff0c;每一步都充满了挑战与创新的火花。…

【Photoshop】PS修改文字内容

Photoshop(PS)修改图片上文字内容&#xff0c;网上教材不少&#xff0c;本人整理实践过的方法&#xff0c;分享给各位。本人实践方法&#xff1a; 内容识别填充&#xff1a;适用于背景色复杂的图片内容修补工具&#xff1a;适用于背景色为纯色的图片 方式一&#xff1a;内容识…

HAL库开发--STM32的HAL环境搭建

知不足而奋进 望远山而前行 目录 文章目录 前言 下载 安装 解压 安装 添加开发包 修改仓库路径 下载软件开发包&#xff08;慢&#xff0c;不推荐&#xff09; 解压已有软件开发包&#xff08;快&#xff0c;推荐&#xff09; 总结 前言 在嵌入式系统开发中&#x…

【数据的增值之路】全生命周期的数据演化过程

引言&#xff1a;随着云计算、大数据、人工智能、区块链等新一代信息技术的快速发展&#xff0c;数据已经成为推动经济增长的重要生产要素。数据量的爆炸式增长&#xff0c;为挖掘数据价值、推动数字经济发展提供了丰富的资源基础。重要概念解析&#xff1a; 数据经济&#xf…

【内存管理之指针艺术】

1.记住&#xff1a;不同的类型具有不同的内存大小 2.指针只是存储地址的变量 3.指针艺术&#xff1a;增长1 4.重来 5.指针艺术&#xff1a;减小1 6.指针艺术 6.下标运算符[] 7.指针图解 7.指向对象的指针 7.指向指针的指针

Java—读取properties配置文件

编写配置文件 usernameroot password123456 urljdbc:mysql://localhost:3306/myDatabase driverClassNamecom.mysql.cj.jdbc.Driver 编写测试类 import java.io.FileInputStream; import java.io.IOException; import java.util.Enumeration; import java.util.Properties;/*…

CCAA质量管理【学习笔记】​​ 备考知识点笔记(四)

第四节 质量非数据资料分析的基础工具 1 关 联 图 2.1 概念 所谓关联图&#xff0c;就是对关系复杂而相互纠缠的问题&#xff0c;依据原因—结果或目的一手段等关系&#xff0c; 在逻辑上用箭头把各要素之间的因果关系连接起来&#xff0c;厘清复杂问题、整理语言文字资料…

神舟电脑文件误删怎么办?这些恢复方法助你轻松解决

神舟电脑文件误删怎么办&#xff1f;在信息爆炸的时代&#xff0c;电脑已经成为我们日常生活和工作中不可或缺的重要工具。然而&#xff0c;有时我们会因为一些不小心的操作&#xff0c;误删了电脑中的重要文件&#xff0c;尤其是在使用神舟电脑这类高性能设备时&#xff0c;文…

编译一个叫:未来的IDE-Zed编辑器(Windows平台)

一、前言 截止到2024-6-15&#xff0c;Zed官方并未给出Windows的二进制安装包&#xff0c;如果想在Windows平台使用的话需要自己编译&#xff0c;我是如何编译的请随我道来&#xff0c;有兴趣的码友可以尝试下&#xff0c;在下可不敢保证各位码友按我这方法能100%编译出来&…

RK3568技术笔记八 开发环境的搭建

先按照前面的方法将 ubuntu 安装在 PC 机上。 编译开发Linux系统&#xff0c;虚拟机Ubuntu 系统要求&#xff1a; 64位系统&#xff0c;硬盘空间大于或等于200G&#xff0c;内存不小于6GB。 建议使用 Ubuntu18.04 系统进行编译。 光盘资料&#xff1a;SAIL-RK3568开发板光盘…

SQL编程基础常见题型练习

SQL编程基础常见题型练习 1. 基础查询1.1. 基础查询1.2. 简单处理查询结果 2. 条件查询2.1. 基础排序2.2. 基础操作符2.3. 高级操作符 3. 高级查询3.1. 计算函数3.2. 分组查询 4. 多表查询4.1. 子查询4.2. 链接查询4.3. 组合查询 5. 必会的常用函数5.1. 条件函数5.2. 日期函数 …

将Jar用三种方式生成Windows的安装程序

无论是WEB(spring boot)的JAR,还是JavaFX以及swing的Jar,要生成windows方式。 打包成Windows可执行文件&#xff08;.exe&#xff09;&#xff0c;你可以使用以下三种方法&#xff1a; ### 方法1&#xff1a;使用Inno Setup 1. **构建JavaFX应用程序**&#xff1a; 使用M…

大模型企业落地:制造业可以选择的应用场景

前言 在当今制造业快速发展的背景下&#xff0c;设备稳定运行对于企业的发展至关重要。然而&#xff0c;传统的设备维修模式已无法满足现代企业的需求。为此&#xff0c;引入智能化、数字化的设备维修解决方案成为必然趋势。本文将探讨如何利用大模型技术&#xff0c;构建企业…

Netflix 机器学习科学家的提示词优化经验分享

编者按&#xff1a; 如何充分发挥大模型的潜能&#xff0c;用好大模型&#xff0c;关键在于如何优化向它们发送的提示词&#xff08;prompt&#xff09;&#xff0c;是为提示词工程&#xff08;prompt engineering&#xff09;。 本文Netflix 机器学习科学家Cameron R. Wolfe的…

FPGA - 全局时钟资源

全局时钟资源是指FPGA内部为实现系统时钟到达FPGA内部各 CLB、IOB&#xff0c;以及BSRAM&#xff08;Block Select RAM&#xff0c;选择性BRAM&#xff09;等基本逻辑单元的延时和抖动最小化&#xff0c;采用全铜层工艺设计和实现的专用缓冲与驱动结构。 由于全局时钟资源的布线…