当前位置:   article > 正文

智能问答机器人_csdn问答机器人在哪

csdn问答机器人在哪

1. 前言

问答机器人现在很多场合都有使用,比如:网页智能客服、微信公众号智能回复、淘宝的售后客服,QQ聊天机器人等等。有了这些客户机器人就能帮我们回答很多预置的一些问题,帮助用户解决常见问题,还可以进行自主训练,得到一个适合自己使用的机器人。机器人也可以关联很多其他的技能,玩小游戏,查询天气、查询节假日、查询很多其他的信息,非常方便。

这篇文章就采用华为云提供的智能问答机器人设计一个小软件,采用华为云提供的API接口完成数据交互,与机器人进行问答交互,通过这个例子可以了解到智能问答机器人的基本功能、使用场景、使用方法等等。

image-20220209135931880

华为云的智能问答机器人特点介绍

提供问答引擎、机器人管理平台来方便客户快速、低成本构建智能问答服务。智能问答能满足用户快速上线、高度定制、数据可控的需求,具有问答准确率高、自主学习等特点。能够帮助企业节省客服人力,大大降低客服响应时间。

具备如下优势点:

  • 智能的问答管理
    • 热点问题、趋势、知识自动分析统计。
    • 支持未知问题自动聚类,匹配相似问答,辅助人工不断扩充知识库。
    • 支持问答调测,点对点的监测智能应答过程。
    • 支持领域知识挖掘,提供易用的标注工具挖掘领域词。
  • 全面的对话管理
    • 支持自然语言多能力融合,智能对话中控。
    • 灵活的知识库管理,支持对知识的批量操作。
    • 支持嵌入多轮对话技能,满足复杂的任务型对话场景。
  • 高效训练部署
    • 基于modelarts的底层算法能力,提供更快的模型训练、部署能力。
    • 支持多算法模型效果验证,验证不同数据、参数、模型对问法效果的影响。
    • 支持模型最优参数组合推荐,保证问答效果。

2. 使用问答机器人服务

2.1 开通服务

地址: https://www.huaweicloud.com/product/cbsqa.html

点击立即使用会进入到购买页面,可以免费体验14天,对于技术评估,场景测试已经足够。

image-20220209093930052

image-20220209093946385

image-20220209094116181

image-20220209094130563

2.2 配置机器人

(1)机器人购买之后,点击进入管理页面,对机器人的属性、技能进行配置,训练。

image-20220209094415424

image-20220209094456180

(2)可以添加预置的技能,还可以添加自定义技能

预置的技能有查询天气、成语接龙、查星座、查节日、猜数字游戏等等。也可以自己自定义技能标注训练发布。

image-20220209094751127

image-20220209094705889

2.3 对话体验

在管理页面右上角可以在线体验与机器人对话,可以快速调试问答效果。

image-20220209131421310

image-20220209131504326

2.4 接口调试

地址: https://support.huaweicloud.com/api-cbs/cbs_03_0115.html

在调用API测试之前,可以先使用在线调试接口测试,了解请求如何发出,有哪些必填参数,请求参数怎么填,返回的结果格式是怎样的。

image-20220209131616278

2.5 API请求总结

(1)请求的URL格式

请求的URL格式: POST /v1/{project_id}/qabots/{qabot_id}/chat
其中参数介绍: 
project_id  是项目ID。
qabot_id 是机器人标识符,qabot编号,UUID格式。如:303a0a00-c88a-43e3-aa2f-d5b8b9832b02。
登录对话机器人服务控制台,在智能问答机器人列表中就可以查看到abot_id。
    
最终拼接的URL格式: https://cbs-ext.cn-north-4.myhuaweicloud.com/v1/0e5957be8a00f53c2fa7c0045e4d8fbf/qabots/5c889415-6834-4ada-aa51-ea5000941e25/chat    
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

image-20220209131851505

(2)请求头与请求参数总结

请求头:  
"X-Auth-Token": "------------",  这是API接口鉴权用的,所有的API请求都要这个参数
"Content-Type": "application/json"
 
请求体: 
{
 "question": "北京天气"  这是给机器人提交的问题,随后机器人会返回答案
}

响应结果:
{
 "request_id": "e3ab440c-0bb2-455b-aff8-07e4cc4115f4",
 "reply_type": 1,
 "taskbot_answers": {
  "answer": "当前北京天气晴,最高8摄氏度,最低-5摄氏度,日间南风≤3级,夜间南风≤3级。",
  "skill_id": "22a20348-aa8b-44d2-96df-dcae1b8d92c2",
  "skill_responses": [
   {
    "frame": {
     "intention": "weather_query",
     "confidence": 1,
     "reply": "当前北京天气晴,最高8摄氏度,最低-5摄氏度,日间南风≤3级,夜间南风≤3级。",
     "intention_alias": "查天气",
     "candidate_words": [],
     "task_complete": true,
     "flow_complete": true,
     "current_slots": [
      {
       "slot_id": "a9ee29df-8f60-4ff1-863e-60e9412a1f95",
       "slot_name": "地点",
       "slot_identification": "loc",
       "slot_values": [
        {
         "word": "北京",
         "norm_word": "北京",
         "begin_position": 0,
         "end_position": 1
        }
       ]
      }
     ],
     "history_slots": []
    },
    "candidate": {
     "candidate_confidence": 0
    },
    "skill_id": "22a20348-aa8b-44d2-96df-dcae1b8d92c2",
    "skill_version": "v50",
    "locked": false,
    "related_intentions": [
     {
      "intention": "weather_query",
      "confidence": 1
     }
    ]
   },
   {
    "frame": {
     "confidence": 0,
     "reply": "你太难理解了,我需要一些信息才能知道呢,哼!",
     "candidate_words": [],
     "task_complete": true,
     "flow_complete": true,
     "current_slots": [],
     "history_slots": []
    },
    "candidate": {
     "candidate_confidence": 0
    },
    "skill_id": "8b71d740-aedb-4c01-8948-460dab64fd22",
    "skill_version": "v67",
    "locked": false,
    "related_intentions": [
     {
      "intention": "constellation",
      "confidence": 0.513
     }
    ]
   },
   {
    "frame": {
     "confidence": 0,
     "reply": "对不起,我没明白,请再多教我一些吧",
     "candidate_words": [],
     "task_complete": true,
     "flow_complete": true,
     "current_slots": [],
     "history_slots": []
    },
    "candidate": {
     "candidate_intention": "chengyu",
     "candidate_confidence": 0.507154
    },
    "skill_id": "9d2aa6d4-8461-4ca7-9db8-af32fdbfde57",
    "skill_version": "v12",
    "locked": true,
    "related_intentions": [
     {
      "intention": "chengyu",
      "confidence": 0.507
     }
    ]
   },
   {
    "frame": {
     "confidence": 0,
     "reply": "对不起,我没明白,请再多教我一些吧",
     "candidate_words": [],
     "task_complete": true,
     "flow_complete": true,
     "current_slots": [],
     "history_slots": []
    },
    "candidate": {
     "candidate_confidence": 0
    },
    "skill_id": "4a93acd4-5a29-4188-b033-9fffd932e5df",
    "skill_version": "v31",
    "locked": true,
    "related_intentions": [
     {
      "intention": "sys.other",
      "confidence": 0.555
     }
    ]
   },
   {
    "frame": {
     "confidence": 0,
     "reply": "对不起,我没明白,请再多教我一些吧",
     "candidate_words": [],
     "task_complete": true,
     "flow_complete": true,
     "current_slots": [],
     "history_slots": []
    },
    "candidate": {
     "candidate_confidence": 0
    },
    "skill_id": "25ad99ee-8a13-40a2-8fa1-0a18370e2ef5",
    "skill_version": "v34",
    "locked": false,
    "related_intentions": [
     {
      "intention": "sys.other",
      "confidence": 0
     }
    ]
   }
  ]
 },
 "session_id": "4b105ca2-28e2-4ec8-bd4b-87c8d7c6a322"
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142
  • 143
  • 144
  • 145
  • 146
  • 147
  • 148
  • 149
  • 150
  • 151
  • 152
  • 153

请求头里的X-Auth-Token字段在之前的文章已经介绍过,获取方法看这里: https://bbs.huaweicloud.com/blogs/317759 翻到2.3小节。

(3)请求参数介绍

详细的参数可以看官方文档介绍: https://support.huaweicloud.com/api-cbs/cbs_03_0115.html

请求参数里一般主要填下面两个字段:

question 这是必填的参数,填用户的问题。如:查天气。长度为1~512。

session_id 填会话标识符,UUID格式。如:c04e6f7b-61d7-4a2d-a0c8-f9ecd2f62359。
每次对话开启,机器人创建会话id,下次请求中传入该id表示继续该轮对话,每轮会话有效时间为2分钟。
若传入的会话id已过期或者为空,则机器人会重新创建新的会话id(重新创建会话id会消耗一定时间)。
比如: 玩成语接龙游戏,就需要填会话标识ID,这样才可以接着上一次的对话继续问答。
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

(4)响应参数介绍

reply_type 表示当前回答的类型
			0 知识库回复。
			1 技能回复。
			2 闲聊回复。
			3 图谱回复。
			4 文档回复。
			5 表格回复。

session_id  这是当前的会话id,每次对话开启,机器人创建会话id,下次请求中传入该id表示继续该对话,每轮会话有效时间为2分钟。

以技能回复为例:  
"taskbot_answers": {
"answer": "当前北京天气晴,最高8摄氏度,最低-5摄氏度,日间南风≤3级,夜间南风≤3级。",
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14

3. 实现效果与案例代码

3.1 实现效果

(1)成语接龙

image-20220209123137225

(2)天气查询

image-20220209133929894

(3)查星座

image-20220209134248235

image-20220209134346517

(4)猜数字游戏

image-20220209134752735

3.2 核心代码

image-20220209134858362

#include "widget.h"
#include "ui_widget.h"

Widget::Widget(QWidget *parent)
    : QWidget(parent)
    , ui(new Ui::Widget)
{
    ui->setupUi(this);

    this->setWindowTitle("智能问答机器人");


    //读取之前保存的token数据
    QString data_token=ReadDataFile();
    if(!data_token.isEmpty())
    {
        Token=data_token.toUtf8();
        qDebug()<<"读取到之前的数据:"<<Token;
    }

    /*网络请求设置*/
    manager = new QNetworkAccessManager(this);
    connect(manager, SIGNAL(finished(QNetworkReply*)), this, SLOT(replyFinished(QNetworkReply*)));

    //机器人
    ui->listWidget->addItem(new QListWidgetItem(QIcon(QObject::tr(":/res/2.ico")), QObject::tr("您好,很高兴为你服务.")));

}


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

/*
功能: 保存数据到文件
*/
void Widget::SaveDataToFile(QString text)
{
    /*保存数据到文件,方便下次加载*/
    QString file;
    file=QCoreApplication::applicationDirPath()+"/"+ConfigFile;
    QFile filesrc(file);
    filesrc.open(QIODevice::WriteOnly);
    QDataStream out(&filesrc);
    out << text;  //序列化写字符串
    filesrc.flush();
    filesrc.close();
}

/*
功能: 从文件读取数据
*/
QString Widget::ReadDataFile(void)
{
    //读取配置文件
    QString text,data;
    text=QCoreApplication::applicationDirPath()+"/"+ConfigFile;

    //判断文件是否存在
    if(QFile::exists(text))
    {
        QFile filenew(text);
        filenew.open(QIODevice::ReadOnly);
        QDataStream in(&filenew); // 从文件读取序列化数据
        in >> data; //提取写入的数据
        filenew.close();
    }
    return data; //返回值读取的值
}

/*
功能: 获取token
*/
void Widget::GetToken()
{
    //表示获取token
    function_select=3;

    QString requestUrl;
    QNetworkRequest request;

    //设置请求地址
    QUrl url;

    //获取token请求地址
    requestUrl = QString("https://iam.%1.myhuaweicloud.com/v3/auth/tokens")
                 .arg(SERVER_ID);

    //自己创建的TCP服务器,测试用
    //requestUrl="http://10.0.0.6:8080";

    //设置数据提交格式
    request.setHeader(QNetworkRequest::ContentTypeHeader, QVariant("application/json;charset=UTF-8"));

    //构造请求
    url.setUrl(requestUrl);

    request.setUrl(url);

    QString text =QString("{\"auth\":{\"identity\":{\"methods\":[\"password\"],\"password\":"
    "{\"user\":{\"domain\": {"
    "\"name\":\"%1\"},\"name\": \"%2\",\"password\": \"%3\"}}},"
    "\"scope\":{\"project\":{\"name\":\"%4\"}}}}")
            .arg(MAIN_USER)
            .arg(IAM_USER)
            .arg(IAM_PASSWORD)
            .arg(SERVER_ID);

    //发送请求
    manager->post(request, text.toUtf8());
}


//解析反馈结果
void Widget::replyFinished(QNetworkReply *reply)
{
    QString displayInfo="";
    int statusCode = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt();

    //读取所有数据
    QByteArray replyData = reply->readAll();

    qDebug()<<"状态码:"<<statusCode;
    qDebug()<<"反馈的数据:"<<QString(replyData);

    //更新token
    if(function_select==3)
    {
        displayInfo="token 更新失败.";
        //读取HTTP响应头的数据
        QList<QNetworkReply::RawHeaderPair> RawHeader=reply->rawHeaderPairs();
        qDebug()<<"HTTP响应头数量:"<<RawHeader.size();
        for(int i=0;i<RawHeader.size();i++)
        {
            QString first=RawHeader.at(i).first;
            QString second=RawHeader.at(i).second;
            if(first=="X-Subject-Token")
            {
                Token=second.toUtf8();
                displayInfo="token 更新成功.";

                //保存到文件
                SaveDataToFile(Token);
                break;
            }
        }
        QMessageBox::information(this,"提示",displayInfo,QMessageBox::Ok,QMessageBox::Ok);
        return;
    }

    //判断状态码
    if(200 != statusCode)
    {
        //解析数据
        QJsonParseError json_error;
        QJsonDocument document = QJsonDocument::fromJson(replyData, &json_error);
        if(json_error.error == QJsonParseError::NoError)
        {
            //判断是否是对象,然后开始解析数据
            if(document.isObject())
            {
                QString error_str="";
                QJsonObject obj = document.object();
                QString error_code;
                //解析错误代码
                if(obj.contains("error_code"))
                {
                    error_code=obj.take("error_code").toString();
                    error_str+="错误代码:";
                    error_str+=error_code;
                    error_str+="\n";
                }
                if(obj.contains("error_msg"))
                {
                    error_str+="错误消息:";
                    error_str+=obj.take("error_msg").toString();
                    error_str+="\n";
                }

                //显示错误代码
                QMessageBox::information(this,"提示",error_str,QMessageBox::Ok,QMessageBox::Ok);
            }
         }
        return;
    }

    //对话返回
    if(function_select==0)
    {
        //解析数据
        QJsonParseError json_error;
        QJsonDocument document = QJsonDocument::fromJson(replyData, &json_error);
        if(json_error.error == QJsonParseError::NoError)
        {
            //判断是否是对象,然后开始解析数据
            if(document.isObject())
            {
                QString error_str="";
                QJsonObject obj = document.object();
                QString answer;

                //解析对话ID
                if(obj.contains("session_id"))
                {
                    session_id=obj.take("session_id").toString();
                    qDebug()<<"持续对话ID: "<<session_id;
                }

                //解析答案
                if(obj.contains("taskbot_answers"))
                {
                    QJsonObject obj1=obj.take("taskbot_answers").toObject();
                    if(obj1.contains("answer"))
                    {
                        answer=obj1.take("answer").toString();
                    }
                }
                qDebug()<<"答案:"<<answer;

                //机器人
                ui->listWidget->addItem(new QListWidgetItem(QIcon(QObject::tr(":/res/2.ico")), answer));

            }
         }
    }
}


//获取对话结果
void Widget::getProblemResult(QString session_id,QString send_text)
{
    //表示获取对话结果
    function_select=0;

    QString requestUrl;
    QNetworkRequest request;

    //设置请求地址
    QUrl url;

    //获取token请求地址
    requestUrl = QString("https://cbs-ext.%1.myhuaweicloud.com/v1/%2/qabots/%3/chat")
                 .arg(SERVER_ID)
                 .arg(PROJECT_ID)
                 .arg(ROBOT_ID);

    //设置数据提交格式
    request.setHeader(QNetworkRequest::ContentTypeHeader, QVariant("application/json"));

    //设置token
    request.setRawHeader("X-Auth-Token",Token);

    //构造请求
    url.setUrl(requestUrl);

    request.setUrl(url);

    QString text =QString("{\"question\": \"%1\",\"session_id\":\"%2\"}").arg(send_text).arg(session_id);

    //发送请求
    manager->post(request, text.toUtf8());
}

//发送问答
void Widget::on_pushButton_send_clicked()
{
    QString text=ui->lineEdit->text();
    if(text.isEmpty())
    {
      return;
    }

    QListWidgetItem *item;
    item=new QListWidgetItem(text);
    item->setTextAlignment(Qt::AlignRight);
    item->setTextColor(QColor("#FF1493"));
    ui->listWidget->addItem(item);

    getProblemResult(session_id,text);
}

//更新token
void Widget::on_pushButton_token_clicked()
{
    GetToken();
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142
  • 143
  • 144
  • 145
  • 146
  • 147
  • 148
  • 149
  • 150
  • 151
  • 152
  • 153
  • 154
  • 155
  • 156
  • 157
  • 158
  • 159
  • 160
  • 161
  • 162
  • 163
  • 164
  • 165
  • 166
  • 167
  • 168
  • 169
  • 170
  • 171
  • 172
  • 173
  • 174
  • 175
  • 176
  • 177
  • 178
  • 179
  • 180
  • 181
  • 182
  • 183
  • 184
  • 185
  • 186
  • 187
  • 188
  • 189
  • 190
  • 191
  • 192
  • 193
  • 194
  • 195
  • 196
  • 197
  • 198
  • 199
  • 200
  • 201
  • 202
  • 203
  • 204
  • 205
  • 206
  • 207
  • 208
  • 209
  • 210
  • 211
  • 212
  • 213
  • 214
  • 215
  • 216
  • 217
  • 218
  • 219
  • 220
  • 221
  • 222
  • 223
  • 224
  • 225
  • 226
  • 227
  • 228
  • 229
  • 230
  • 231
  • 232
  • 233
  • 234
  • 235
  • 236
  • 237
  • 238
  • 239
  • 240
  • 241
  • 242
  • 243
  • 244
  • 245
  • 246
  • 247
  • 248
  • 249
  • 250
  • 251
  • 252
  • 253
  • 254
  • 255
  • 256
  • 257
  • 258
  • 259
  • 260
  • 261
  • 262
  • 263
  • 264
  • 265
  • 266
  • 267
  • 268
  • 269
  • 270
  • 271
  • 272
  • 273
  • 274
  • 275
  • 276
  • 277
  • 278
  • 279
  • 280
  • 281
  • 282
  • 283
  • 284
  • 285
  • 286
  • 287
  • 288
声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/花生_TL007/article/detail/420494
推荐阅读
相关标签
  

闽ICP备14008679号