汇川伺服电机位置控制模式QT程序Demo实现

news2024/10/7 4:27:10

0.实现效果

 

1.工程文件

#-------------------------------------------------
#
# Project created by QtCreator 2022-11-30T09:37:26
#
#-------------------------------------------------

QT       += core gui
QT       += serialport

greaterThan(QT_MAJOR_VERSION, 4): QT += widgets

TARGET = SerialServo
TEMPLATE = app

# The following define makes your compiler emit warnings if you use
# any feature of Qt which has been marked as deprecated (the exact warnings
# depend on your compiler). Please consult the documentation of the
# deprecated API in order to know how to port your code away from it.
DEFINES += QT_DEPRECATED_WARNINGS

# You can also make your code fail to compile if you use deprecated APIs.
# In order to do so, uncomment the following line.
# You can also select to disable deprecated APIs only up to a certain version of Qt.
#DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0x060000    # disables all the APIs deprecated before Qt 6.0.0

CONFIG += c++11

SOURCES += \
        console.cpp \
        main.cpp \
        mainwindow.cpp \
        settingsdialog.cpp

HEADERS += \
        console.h \
        mainwindow.h \
        settingsdialog.h

FORMS += \
        mainwindow.ui \
        settingsdialog.ui

# Default rules for deployment.
qnx: target.path = /tmp/$${TARGET}/bin
else: unix:!android: target.path = /opt/$${TARGET}/bin
!isEmpty(target.path): INSTALLS += target

RESOURCES += \
    serialservo.qrc

2. 接受显示区

#ifndef CONSOLE_H
#define CONSOLE_H

#include <QPlainTextEdit>

class Console : public QPlainTextEdit
{
    Q_OBJECT

signals:
    void getData(const QByteArray &data);

public:
    explicit Console(QWidget *parent = nullptr);

    void putData(const QByteArray &data);
    void setLocalEchoEnabled(bool set);

protected:
    void keyPressEvent(QKeyEvent *e) override;
    void mousePressEvent(QMouseEvent *e) override;
    void mouseDoubleClickEvent(QMouseEvent *e) override;
    void contextMenuEvent(QContextMenuEvent *e) override;

private:
    bool m_localEchoEnabled = false;
};

#endif // CONSOLE_H

实现文件

#include "console.h"

#include <QScrollBar>

Console::Console(QWidget *parent) :
    QPlainTextEdit(parent)
{
    document()->setMaximumBlockCount(100);
    QPalette p = palette();
    p.setColor(QPalette::Base, Qt::black);
    p.setColor(QPalette::Text, Qt::green);
    setPalette(p);
}

void Console::putData(const QByteArray &data)
{
    insertPlainText(data);

//    QScrollBar *bar = verticalScrollBar();
//    bar->setValue(bar->maximum());
}

void Console::setLocalEchoEnabled(bool set)
{
    m_localEchoEnabled = set;
}

void Console::keyPressEvent(QKeyEvent *e)
{
    switch (e->key()) {
    case Qt::Key_Backspace:
    case Qt::Key_Left:
    case Qt::Key_Right:
    case Qt::Key_Up:
    case Qt::Key_Down:
        break;
    default:
        if (m_localEchoEnabled)
            QPlainTextEdit::keyPressEvent(e);
        emit getData(e->text().toLocal8Bit());
    }
}

void Console::mousePressEvent(QMouseEvent *e)
{
    Q_UNUSED(e)
    setFocus();
}

void Console::mouseDoubleClickEvent(QMouseEvent *e)
{
    Q_UNUSED(e)
}

void Console::contextMenuEvent(QContextMenuEvent *e)
{
    Q_UNUSED(e)
}

3. 主程序

#include "mainwindow.h"
#include <QApplication>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    MainWindow w;
    w.show();

    return a.exec();
}

4. 主窗体程序

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QMainWindow>
#include <QSerialPort>

QT_BEGIN_NAMESPACE

class QLabel;

namespace Ui {
class MainWindow;
}

QT_END_NAMESPACE

class Console;
class SettingsDialog;

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    explicit MainWindow(QWidget *parent = nullptr);
    ~MainWindow();

    QByteArray hexString2ByteArray(QString HexString);
    uint16_t comCrcValue(const uint8_t* data, uint16_t length);

signals:
    void VDI1cmd(const QString &s);
    void VDI2cmd(const QString &s);
    void VDO1cmd(const QString &s);
    void Modelcmd(const QString &s);
    void ComVDIcmd(const QString &s);
    void ComVDOcmd(const QString &s);
    void ComVDIDefaultcmd(const QString &s);
    void DI5Funccmd(const QString &s);
    void CmdSourcecmd(const QString &s);
    void MulStageModcmd(const QString &s);
    void Displacementcmd(const QString &s);
    void PosAbsLinearcmd(const QString &s);
    void RunMotorcmd(const QString &s);

    void FillDisplacementcmd(const QString &s);

private slots:
    void openSerialPort();
    void closeSerialPort();
    void about();
    void writeData(const QByteArray &data);
    void readData();
    void saveSettings();

    void handleError(QSerialPort::SerialPortError error);

    void on_pushButtonRun_clicked();

    void on_pushButtonEnable_clicked();

    void on_pushButtonDisable_clicked();

    void sendCommands(QString strcommands);
    void fillDisplacement(QString strcommands);

private:
    void initActionsConnections();
    void initCommandsConnections();

private:
    void showStatusMessage(const QString &message);

    Ui::MainWindow *m_ui = nullptr;
    QLabel *m_status = nullptr;
    Console *m_console = nullptr;
    SettingsDialog *m_settings = nullptr;
    QSerialPort *m_serial = nullptr;

    long m_displacement;
};

#endif // MAINWINDOW_H


实现文件:

#include "mainwindow.h"
#include "ui_mainwindow.h"
#include "console.h"
#include "settingsdialog.h"

#include <QLabel>
#include <QMessageBox>

#include <QDebug>
#include <QThread>

const int SLEEPMS = 50;

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    m_ui(new Ui::MainWindow),
    m_status(new QLabel),
    m_console(new Console),
    m_settings(new SettingsDialog),
    m_serial(new QSerialPort(this))
   ,m_displacement(0)
{
    m_ui->setupUi(this);

    setWindowTitle(tr("Servo Motor Demo"));

//    m_console->setEnabled(false);
//    setCentralWidget(m_console);

    m_ui->actionConnect->setEnabled(true);
    m_ui->actionDisconnect->setEnabled(false);
    m_ui->actionQuit->setEnabled(true);
    m_ui->statusBar->addWidget(m_status);

    initActionsConnections();
    initCommandsConnections();

    connect(m_serial, &QSerialPort::errorOccurred, this, &MainWindow::handleError);
    connect(m_serial, &QSerialPort::readyRead, this, &MainWindow::readData);
//    connect(m_console, &Console::getData, this, &MainWindow::writeData);
}

MainWindow::~MainWindow()
{
    delete m_ui;
    delete m_settings;
}

void MainWindow::openSerialPort()
{
    const SettingsDialog::Settings p = m_settings->settings();
    m_serial->setPortName(p.name);
    m_serial->setBaudRate(p.baudRate);
    m_serial->setDataBits(p.dataBits);
    m_serial->setParity(p.parity);
    m_serial->setStopBits(p.stopBits);
    m_serial->setFlowControl(p.flowControl);
    if(m_serial->open(QIODevice::ReadWrite)){
//        m_console->setEnabled(true);
//        m_console->setLocalEchoEnabled(p.localEchoEnabled);
        m_ui->actionConnect->setEnabled(false);
        m_ui->actionDisconnect->setEnabled(true);
        m_ui->actionConfigure->setEnabled(false);

        showStatusMessage(tr("Connect to %1 :%2, %3, %4, %5, %6")
                          .arg(p.name).arg(p.stringBaudRate).arg(p.stringDataBits)
                          .arg(p.stringParity).arg(p.stringStopBits).arg(p.stringFlowControl));
    } else {
        QMessageBox::critical(this, tr("Error"), m_serial->errorString());
        showStatusMessage(tr("Open error"));
    }
}

void MainWindow::closeSerialPort()
{
    if(m_serial->isOpen())
    {
        m_serial->close();
    }
//    m_console->setEnabled(false);
    m_ui->actionConnect->setEnabled(true);
    m_ui->actionDisconnect->setEnabled(false);
    m_ui->actionConfigure->setEnabled(true);
    showStatusMessage(tr("Disconnected"));
}

void MainWindow::about()
{
    QMessageBox::about(this, "About Serial Servo",
                       tr("Serial Servo Demo"));
}

uint16_t MainWindow::comCrcValue(const uint8_t* data, uint16_t length)
{
    uint16_t crcValue = 0xffff;
    int i;
    while (length--)
    {
        crcValue ^= *data++;
        for (i = 0; i < 8; i++)
        {
            if (crcValue & 0x0001)
            {
                crcValue = (crcValue >> 1) ^ 0xA001;
            }
            else
            {
                crcValue = crcValue >> 1;
            }
        }
    }
    return (crcValue);
}

void MainWindow::saveSettings()
{
    QString strVDI1cmd =  QString("01 06 17 00 00 01 4D BE");
    QString strVDI2cmd =  QString("01 06 17 02 00 1C 2C 77");
    QString strVDO1cmd =  QString("01 06 17 21 00 05 1C 77");
    QString strModelcmd =  QString("01 06 02 00 00 01 49 B2");
    QString strComVDIcmd =  QString("01 06 0C 09 00 01 9B 58");
    QString strComVDOcmd =  QString("01 06 0C 0B 00 01 3A 98");
    QString strComVDIDefaultcmd =  QString("01 06 0C 0A 00 01 6B 58");
    QString strDI5Funccmd =  QString("01 06 03 0A 00 00 A9 8C");
    QString strCmdSourcecmd =  QString("01 06 05 00 00 02 08 C7");
    QString strMulStageModcmd =  QString("01 06 11 00 00 00 8C F6");
    QString strDisplacementcmd =  QString("01 10 11 0C 00 02 04 C3 50 00 00 0F FF");
    QString strPosAbsLinearcmd =  QString("01 06 02 01 00 01 18 72");

    if(m_ui->checkBoxVDI1->checkState() == Qt::Checked)
    {
        emit VDI1cmd(strVDI1cmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxVDI2->checkState() == Qt::Checked)
    {
        emit VDI2cmd(strVDI2cmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxVDO1->checkState() == Qt::Checked)
    {
        emit VDO1cmd(strVDO1cmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxModel->checkState() == Qt::Checked)
    {
        emit Modelcmd(strModelcmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxComVDI->checkState() == Qt::Checked)
    {
        emit ComVDIcmd(strComVDIcmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxComVDO->checkState() == Qt::Checked)
    {
        emit ComVDOcmd(strComVDOcmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxComVDIDefault->checkState() == Qt::Checked)
    {
        emit ComVDIDefaultcmd(strComVDIDefaultcmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxDI5Func->checkState() == Qt::Checked)
    {
        emit DI5Funccmd(strDI5Funccmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxCmdSource->checkState() == Qt::Checked)
    {
        emit CmdSourcecmd(strCmdSourcecmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxMulStageMod->checkState() == Qt::Checked)
    {
        emit MulStageModcmd(strMulStageModcmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxDisplacement->checkState() == Qt::Checked)
    {
        emit Displacementcmd(strDisplacementcmd);
        QThread::msleep(SLEEPMS);
    }

    if(m_ui->checkBoxPosAbsLinear->checkState() == Qt::Checked)
    {
        emit PosAbsLinearcmd(strPosAbsLinearcmd);
        QThread::msleep(SLEEPMS);
    }
}

void MainWindow::sendCommands(QString strcommands)
{
    QByteArray settingCmd;
    settingCmd = hexString2ByteArray(strcommands);
    writeData(settingCmd);
}

void MainWindow::writeData(const QByteArray &data)
{
    m_serial->write(data);
    m_serial->waitForBytesWritten(1000);
}

void MainWindow::readData()
{
    const QByteArray data = m_serial->readAll();
//    m_console->putData(data);
}

void MainWindow::handleError(QSerialPort::SerialPortError error)
{
    if(error == QSerialPort::ResourceError){
        QMessageBox::critical(this, tr("Critical Error"), m_serial->errorString());
        closeSerialPort();
    }
}

void MainWindow::initActionsConnections()
{
    connect(m_ui->actionConnect, &QAction::triggered, this, &MainWindow::openSerialPort);
    connect(m_ui->actionDisconnect, &QAction::triggered, this, &MainWindow::closeSerialPort);
    connect(m_ui->actionQuit, &QAction::triggered, this, &MainWindow::close);
    connect(m_ui->actionConfigure, &QAction::triggered, m_settings, &SettingsDialog::show);
//    connect(m_ui->actionClear, &QAction::triggered, m_console, &Console::clear);
    connect(m_ui->actionAbout, &QAction::triggered, this, &MainWindow::about);
    connect(m_ui->actionSaveSetting, &QAction::triggered, this, &MainWindow::saveSettings);
}

void MainWindow::initCommandsConnections()
{
    connect(this, &MainWindow::VDI1cmd, this, &MainWindow::sendCommands);
    connect(this, &MainWindow::VDI2cmd, this, &MainWindow::sendCommands);
    connect(this, &MainWindow::VDO1cmd, this, &MainWindow::sendCommands);
    connect(this, &MainWindow::Modelcmd, this, &MainWindow::sendCommands);

    connect(this, &MainWindow::ComVDIcmd, this, &MainWindow::sendCommands);
    connect(this, &MainWindow::ComVDOcmd, this, &MainWindow::sendCommands);
    connect(this, &MainWindow::ComVDIDefaultcmd, this, &MainWindow::sendCommands);
    connect(this, &MainWindow::DI5Funccmd, this, &MainWindow::sendCommands);

    connect(this, &MainWindow::CmdSourcecmd, this, &MainWindow::sendCommands);
    connect(this, &MainWindow::MulStageModcmd, this, &MainWindow::sendCommands);
    connect(this, &MainWindow::Displacementcmd, this, &MainWindow::sendCommands);
    connect(this, &MainWindow::PosAbsLinearcmd, this, &MainWindow::sendCommands);

    connect(this, &MainWindow::RunMotorcmd, this, &MainWindow::sendCommands);
    connect(this, &MainWindow::FillDisplacementcmd, this, &MainWindow::fillDisplacement);
}

void MainWindow::showStatusMessage(const QString &message)
{
    m_status->setText(message);
}

QByteArray MainWindow::hexString2ByteArray(QString HexString)
{
    bool ok;
    QByteArray ret;
    HexString = HexString.trimmed();
    HexString = HexString.simplified();
    QStringList sl = HexString.split(" ");

    foreach (QString s, sl) {
        if(!s.isEmpty())
        {
            char c = s.toInt(&ok,16) & 0xFF;
            if(ok){
                ret.append(c);
            }else{
                qDebug()<<"invalid hex string"<<s;
            }
        }
    }
    return ret;
}

void MainWindow::fillDisplacement(QString strcommands)
{
//   QString strDisplacement = m_ui->lineEditDisplacement->text();
   QString strDisplacement = strcommands;
   long ldisplacement = strDisplacement.toLong();
   if((ldisplacement < 10000) || (ldisplacement > 100000))
   {
       QMessageBox::warning(this,"Warning","Please enter the value between 10000 and 100000");
       qDebug() << "invalid value: should be between 10000 and 100000" << endl;
       return;
   }

   QByteArray runCmd;

   uint16_t a;
   uint16_t dataLow;
   uint16_t dataHigh;
   uint8_t data[13];
   data[0] = 0x01;
   data[1] = 0x10;
   data[2] = 0x11;
   data[3] = 0x0C;

   data[4] = 0x00;
   data[5] = 0x02;
   data[6] = 0x04;

   dataLow = ldisplacement & 0xffff;
   dataHigh = (ldisplacement >> 16) & 0xffff;

   data[7] = (dataLow >> 8) & 0xff;
   data[8] = dataLow & 0xff;
   data[9] = (dataHigh >> 8) & 0xff;
   data[10] = dataHigh & 0xff;

   a = comCrcValue(data, 11);
   data[11] = a & 0xff;
   data[12] = (a >> 8) & 0xff;

   QString request= QString("");
   for (int i=0; i<13;i++) {
       request += QString("%1 ").arg(data[i],2,16,QChar('0'));
   }

   runCmd = hexString2ByteArray(request);
   writeData(runCmd);

}

void MainWindow::on_pushButtonRun_clicked()
{
       long longTemp = m_ui->lineEditDisplacement->text().toLong();
       if (m_displacement != longTemp)
       {
           m_displacement = longTemp;
           emit FillDisplacementcmd(m_ui->lineEditDisplacement->text());
           QThread::msleep(SLEEPMS);
       }


       QString strRunMotorcmd =  QString("01 06 31 00 00 03 C7 37");
       emit RunMotorcmd(strRunMotorcmd);
       QThread::msleep(SLEEPMS);
}

void MainWindow::on_pushButtonEnable_clicked()
{
    QString strEnableMotorcmd =  QString("01 06 31 00 00 01 46 F6");

    QByteArray runCmd;
    runCmd = hexString2ByteArray(strEnableMotorcmd);
    writeData(runCmd);
}

void MainWindow::on_pushButtonDisable_clicked()
{
    QString strDisableMotorcmd =  QString("01 06 31 00 00 00 87 36");

    QByteArray runCmd;
    runCmd = hexString2ByteArray(strDisableMotorcmd);
    writeData(runCmd);
}

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

JAVA实现数组模拟队列

队列本身是有序列表&#xff0c;若使用数组的结构来存储队列的数据&#xff0c;则队列数组的声明如下图, 其中 maxSize 是该队列的最大容量。 因为队列的输出、输入是分别从前后端来处理&#xff0c;因此需要两个变量 front及 rear分别记录队列前后端的下标&#xff0c;front 会…

RepVGG论文理解与代码分析

最近&#xff0c;看到很多轻量化工作是基于RepVGG改进而来&#xff0c;决定重新回顾一下RepVGG&#xff0c;并在此记录一些理解与心得。 论文地址&#xff1a;https://arxiv.org/abs/2101.03697 Introduction RepVGG通过结构重参数化思想&#xff0c;让训练网络的多路结构(多…

[附源码]JAVA毕业设计-高中辅助教学系统-(系统+LW)

[附源码]JAVA毕业设计-高中辅助教学系统-&#xff08;系统LW&#xff09; 目运行 环境项配置&#xff1a; Jdk1.8 Tomcat8.5 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技…

[附源码]Python计算机毕业设计Django电商小程序

项目运行 环境配置&#xff1a; Pychram社区版 python3.7.7 Mysql5.7 HBuilderXlist pipNavicat11Djangonodejs。 项目技术&#xff1a; django python Vue 等等组成&#xff0c;B/S模式 pychram管理等等。 环境需要 1.运行环境&#xff1a;最好是python3.7.7&#xff0c;…

「湖仓一体」释放全量数据价值!巨杉数据库亮相2022沙丘大会

近日&#xff0c;由数字化研究与知识服务平台沙丘社区主办的2022沙丘大会成功举办&#xff0c;巨杉数据库受邀出席大会&#xff0c;并在湖仓一体专场进行《湖仓一体释放全量数据价值》的主题演讲。 近日&#xff0c;由数字化研究与知识服务平台沙丘社区主办的2022沙丘大会以线上…

低代码开发平台助力生产管理:采购成本管理的优化

采购是企业经营活动中的重要环节&#xff0c;它处于企业生产经营活动的最前端&#xff0c;同时也是成本费用中占较大比重的环节。采购成本主要是指企业在生产过程中用于采购产品及服务等交易活动所产生的一系列支出&#xff0c;包括物资的购买价格、税费、运输费等&#xff0c;…

X电容和Y电容

X电容和Y电容 1安规电容 安规电容之所以称之为安规&#xff0c;它是指用于这样的场合&#xff1a;即电容器失效后&#xff0c;不会导致电击&#xff0c;也不危及人身安全。安规电容包含X电容和Y电容两种&#xff0c;它普通电容不一样的是&#xff0c;普通电容即使在外部电源断…

从0到1 Webpack搭建Vue3开发、生产环境

起步 创建项目目录 mkdir webpack-vue3-demo初始化 package.json npm init -y参考文档 安装 webpack webpack-cli webpack-dev-server webpack-merge npm install webpack webpack-cli webpack-dev-server webpack-merge --save-dev创建配置文件 mkdir build cd build …

vscode配置git和c++

vscode配置git和cvscode配置c1.必要配置2.可选配置配置git1.命令行使用git2.IDE使用git3.一点补充过滤文件设置别名之前一直在用vscodepython做实验&#xff0c;现在想利用vscode复习下c和git顺便做做力扣。vscode配置c 1.必要配置 由于vscode只是个编辑器&#xff0c;所以首…

JVM之运行时数据区 面试相关

JVM创建对象的方式创建对象的步骤内存布局对象访问定位![请添加图片描述](https://img-blog.csdnimg.cn/fa106bd4936440b28e1c359d57ba4d25.png)直接内存创建对象的方式 new 常见方式 Xxx静态方法 XxxBuilder/XxxFactory的静态方法Class的newInstance() 反射&#xff0c;只能空…

魔兽世界开服架设服务器搭建教程

魔兽世界开服架设服务器搭建教程 准备工具&#xff1a; 1、装有windows98/2000/xp/2003系统、内存至少256M的电脑一台 2、魔兽服务器端一个 3、服务器一台&#xff08;魔兽世界对服务器的配置要求并不是很高&#xff0c;CPU 16核 、16线程 带宽最好是选择50M的&#xff0c;游戏…

美食杰项目 -- 发布菜谱(七)

目录前言&#xff1a;具体实现思路&#xff1a;步骤&#xff1a;1. 展示美食杰发布菜谱页效果2. 引入element-ui3. 代码总结&#xff1a;前言&#xff1a; 本文给大家讲解&#xff0c;美食杰项目中 实现发布菜谱页的效果&#xff0c;和具体代码。 具体实现思路&#xff1a; 按…

骑行运动耳机哪个好,列举五款适合在骑行过程中佩戴的耳机

谈起耳机&#xff0c;人们第一印象应该是传统的入耳式耳机&#xff0c;这种耳机在音质以及体积上确实占据了一定的优势&#xff0c;但还是存在着不少的缺点&#xff0c;特别是佩戴的过程中会让我们的耳道保持堵塞状态&#xff0c;导致中耳炎等疾病的频频发生&#xff0c;而这两…

ASEMI-KBL410是什么元器件,kbl410整流桥参数

编辑-Z 俗话说&#xff0c;时势造英雄&#xff0c;整流桥大军中有一款整流桥KBL410有哪些你所不知道的&#xff1f;KBL410是什么元器件&#xff1f;kbl410整流桥参数是多少&#xff1f; KBL410参数描述 型号&#xff1a;KBL410 封装&#xff1a;KBL-4 电性参数&#xff1a;…

ARC113D题解

ARC113D - Sky Reflector 题目大意 有一个nnn行mmm列的表格&#xff0c;你可以在每个表格中填入一个111到kkk之间的整数&#xff0c;定义序列A,BA,BA,B如下&#xff1a; 对于每一个i1,2,…,ni1,2,\dots,ni1,2,…,n&#xff0c;AiA_iAi​是第iii行的最小值对于每一个j1,2,…,…

强化学习:Actor-Critic、SPG、DDPG、MADDPG

马尔可夫决策过程&#xff08;MDP&#xff09; MDP 由元组 (S,A,P,R,γ)(S, A, P, R, \gamma)(S,A,P,R,γ) 描述&#xff0c;分别表示有限状态集、有限动作集、状态转移概率、回报函数、折扣因子 。与马尔可夫过程不同&#xff0c;MDP的状态转移概率是包含动作的&#xff0c;即…

Express 7 指南 - 开发中间件

Express Express 中文网 本文仅用于学习记录&#xff0c;不存在任何商业用途&#xff0c;如侵删 文章目录Express7 指南 - 开发中间件7.1 概述7.2 例子7.2.1 中间件函数 myLogger7.2.2 中间件函数 requestTime7.2.3 中间件函数 validateCookies7.3 可配置的中间件7 指南 - 开发…

中断系统中的设备树__Linux对中断处理的框架及代码流程简述

1 异常向量入口: arch\arm\kernel\entry-armv.S .section .vectors, "ax", %progbits .L__vectors_start: W(b) vector_rst W(b) vector_und W(ldr) pc, .L__vectors_start 0x1000 W(b) vector_pabt W(b) vector_dabt W(b) …

14 【接口规范和业务分层】

14 【接口规范和业务分层】 1.接口规范-RESTful架构 1.1 什么是REST REST全称是Representational State Transfer&#xff0c;中文意思是表述&#xff08;编者注&#xff1a;通常译为表征&#xff09;性状态转移。 它首次出现在2000年Roy Fielding的博士论文中&#xff0c;R…