#include "regularinvestment.h"
|
#include "ui_regularinvestment.h"
|
#include <QDebug>
|
#include <QJsonArray>
|
#include <QJsonDocument>
|
#include <QJsonObject>
|
#include <qfile.h>
|
#include <qnetworkcookie.h>
|
#include <qnetworkreply.h>
|
#include <QDebug>
|
|
RegularInvestment::RegularInvestment(QWidget *parent) :
|
QMainWindow(parent),
|
ui(new Ui::RegularInvestment)
|
{
|
ui->setupUi(this);
|
ui->statusbar->hide();
|
ui->dateTimeEdit->setDateTime(QDateTime::currentDateTime());
|
|
m_nameCodes["长江电力"]= "SH600900";
|
m_nameCodes["中国神华"]= "SH601088";
|
m_nameCodes["中国电信"]= "SH601728";
|
m_nameCodes["中国移动"]= "SH600941";
|
|
|
// 处理数据爬取的操作
|
// 模拟浏览器的参数
|
QString userAgent = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/114.0.0.0 Safari/537.36";
|
m_cookie = "__utma=1.731742638.1647403301.1699341909.1700229030.32; device_id=196eef62baf016c7d95a22752d9bdbab; smidV2=20240414233939e95389ecf7ecd2f4d08524ce770aacd500753aa68e9640320; s=c611de27gr; cookiesu=651726298794778; xq_a_token=220b0abef0fac476d076c9f7a3938b7edac35f48; xqat=220b0abef0fac476d076c9f7a3938b7edac35f48; xq_r_token=1d46f0ed628506486164e5055a4993f9b54b2f4c; xq_id_token=eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJ1aWQiOi0xLCJpc3MiOiJ1YyIsImV4cCI6MTcyOTIxMjc4NCwiY3RtIjoxNzI3NDkwOTU3MjA0LCJjaWQiOiJkOWQwbjRBWnVwIn0.C_GmKEhTaaioDMLWkgZyMXDl4duYEVmsdJHsTi7gbcNz0Tohc-uxHsaw0yBT5k-qmbrJ_RaLMCSxy06v14-R3dwL-MsiKRHxHa5qvQZN4BjEgvPRkqqvPgE_fkPLte8qQOEgd5iVkhr-4mjip0-9WCeXYiH7DygxFOBXGlgoPtpPzAtOTm5TWJmXh0ipDsIZxfNOl8jipXYaIdkv_kqLul5gqiBi5qqnwONDa24Zx-Kvpm8ySWiPFBLzZBqTuRBs4oKAMpSdOiYGLVL7dcSDDZyWqAexmrN4f19hkmd6gBHL4dCczRMDGYc1e98sQtlbZ5lgeEuuM24jjcuwCxsxXQ; u=651726298794778; Hm_lvt_1db88642e346389874251b5a1eded6e3=1727099939,1727251802,1727488707,1727491020; HMACCOUNT=1628106D67895387; acw_tc=2760828017275244258732552e9880f861be6db0c40facbdd5f223490decc2; acw_sc__v2=66f7ee8290dc3f63112948801ef331b8c97ccb35; Hm_lpvt_1db88642e346389874251b5a1eded6e3=1727524485; .thumbcache_f24b8bbe5a5934237bbc0eda20c1b6e7=t00N841S/BEpxTGOoJrbm0blWik12om0ew/whcq/V2DNtyEA8um7J+yzeGOli+6iP/TrvrH0YKH2kHlsmDb5EQ%3D%3D; ssxmod_itna=YqAOBKYve+x0ODfxBcDB4DKM7RtAA4454DkDIEC+GAqGNK3DZDiqAPGhDC8RzeL4Ko7+e2aeQvSeopd5pYDk0Ge5TB0PIjaIDB3DEx06TCCQxiiSDCeDIDWeDiDG4Gm4qGtDpxG=DjDytZ9TtDm4GWGqDmDGYBWqDgDYQDGwIXD7QDIqtW07tQDDNQKpAKDiYeHlL5uMRMtOrK7DtDjdTD/3+kZCbCcPwVFeFO=nPcDB6wxBjZRq00Un+g4mNqLYf4IDAxQuYKtgheYYoAfDhTKhhLSGx4tGY4+GDKSiMS2DDAIvdKeD; ssxmod_itna2=YqAOBKYve+x0ODfxBcDB4DKM7RtAA4454DkDIEC+GDA69mqD/YttDFhxMltFKApT7bCMH+bytp7GQQyCbBWukeAF3+jxeN2wLjbQAFcdwbeNeoohjQ4qtEnLg4TKyX2LqVL=CGaV=GqZZqbDby8DFnFbgWiZEH8zoBzBCbzqWeqwoPq7/TpL=gIRY8sVhEpnWWHQU8sz+S8=+8oRerHq0wtQnSzyQDK7Dmvr3a+VY7fezRmxKF=bDeqexYUbuuzw2eR3In9evW6tzHbQY6vp=AIOUc9l6vc0vOl9plD6D07zGGQ41uxpii2Y5s7KvYQDWGYExD7=DYKKeD==";
|
QByteArray cookieByte = m_cookie.toUtf8();
|
QList<QNetworkCookie> list;
|
list.push_back(QNetworkCookie(cookieByte));
|
|
QVariant var;
|
var.setValue(list);
|
// 设置要访问的网址
|
m_request.setUrl(QUrl("https://xueqiu.com/?md5__1038=QqGxcDnDyiitnD05o4%2Br%3Di%3De0KDtYqCDRWOoD"));
|
// 设置请求头,用户代理,用来模拟浏览器
|
m_request.setHeader(QNetworkRequest::UserAgentHeader,userAgent);
|
// 设置cookie
|
//m_request.setHeader(QNetworkRequest::CookieHeader, var);
|
|
// 查看manager都支持哪些协议
|
qDebug()<<"定投管理--支持的协议:"<<m_manager.supportedSchemes();
|
// 关联信号槽,当请求管理对象完全打开网页之后,会将数据给槽函数处理
|
connect(&m_manager,SIGNAL(finished(QNetworkReply*)),this,SLOT(showAplyData(QNetworkReply*)));
|
|
// 去请求首页
|
m_manager.get(m_request);
|
|
// 处理模型
|
m_model = new QStandardItemModel(0,7,this);
|
ui->tableView->setModel(m_model);
|
QStringList labels;
|
labels<<"时间"<<"买入价格"<<"数量(手)"<<"所需金额(元)"<<"最新价格"<<"盈亏比"<<"盈亏金额";
|
m_model->setHorizontalHeaderLabels(labels);
|
|
|
}
|
|
RegularInvestment::~RegularInvestment()
|
{
|
delete ui;
|
}
|
|
void RegularInvestment::showClosePrice(QString name, QString closePrice)
|
{
|
qDebug()<<name<<closePrice;
|
ui->label_closePrice->setText(closePrice);
|
|
on_lineEdit_2_returnPressed(); // 刷新总价
|
}
|
|
void RegularInvestment::on_comboBox_currentIndexChanged(const QString &arg1)
|
{
|
|
qDebug()<<"当前股票为:"<<arg1;
|
emit getClosePriceSignal(arg1);
|
|
}
|
|
void RegularInvestment::on_lineEdit_2_returnPressed()
|
{
|
qDebug()<<ui->lineEdit_2->text();
|
double price = ui->lineEdit_2->text().toInt()* 100 * ui->label_closePrice->text().toDouble();
|
ui->lineEdit->setText(QString::number(price));
|
}
|
|
void RegularInvestment::on_pushButton_clicked()
|
{
|
m_model->setRowCount(0);
|
// 按指定时间开始,往后递增月来投入,进行统计
|
qDebug()<<"执行定投回测";
|
// emit sendInfoMess("<font size=12 color=pink>执行MACD策略 </font>");
|
// int curRow = ui->tableView->currentIndex().row();
|
// QString symbol = m_model->item(curRow,1)->text();
|
|
QString name = ui->comboBox->currentText();
|
QString symbol = m_nameCodes[name];
|
qint64 begin = QDateTime::currentMSecsSinceEpoch(); // 取当前时间戳
|
int numsCnt = 1;
|
QString period = ui->comboBox_2->currentText();
|
QString type = period == "月" ? "month" : "year" ;
|
QDateTime beginDate = ui->dateTimeEdit->dateTime(); // 可以按月增加来求价格,然后和最新的价格比较看收益情况
|
while (beginDate.toMSecsSinceEpoch() <= begin) {
|
qint64 start = beginDate.toMSecsSinceEpoch();
|
QString urlStr = QString("https://stock.xueqiu.com/v5/stock/chart/kline.json?symbol=%1&begin=%2&period=%3&type=before&count=-%4&indicator=kline,macd").arg(symbol).arg(start).arg(type).arg(numsCnt);
|
qDebug()<<urlStr;
|
qDebug()<<"当前股票:"<<symbol<<name;
|
// 下一步就是根据url请求到的数据,进行分析
|
//m_menuIndex = 3; // 第四个菜单项
|
m_request.setUrl(QUrl(urlStr));
|
m_manager.get(m_request);
|
beginDate = beginDate.addMonths(1); // 增加一个月
|
}
|
|
|
}
|
|
void RegularInvestment::showAplyData(QNetworkReply *reply)
|
{
|
qDebug()<<"收到响应";
|
// 将响应的数据,一把读取完,放到字节数组里面来处理
|
QByteArray buffer = reply->readAll();
|
|
// 将数据写到文件中,方便观察数据内容
|
QFile file("data_dingtou.txt");
|
file.open(QIODevice::ReadWrite | QIODevice::Text);
|
QTextStream out(&file);
|
out << buffer << endl;
|
file.close();
|
|
// 下面使用JSON进行数据处理
|
if(reply->url().toString().indexOf("https://xueqiu.com/") != -1){
|
qDebug()<<"发现首页url";
|
qDebug()<<buffer;
|
|
}else if(reply->url().toString().indexOf("https://stock.xueqiu.com/v5/stock/chart/kline.json") != -1){
|
qDebug()<<"查看个股情况:";
|
getOneStock(buffer);
|
|
}
|
}
|
|
/* 要处理的单个股票的格式如下
|
{"data":{" ":"SH601127","column":["timestamp","volume","open","high","low","close","chg","percent","turnoverrate","amount","volume_post","amount_post"],
|
"item":[[1680192000000,592214010,37.57,41.56,35.63,37.85,0.2,0.53,50.63,2.3075281252E10,0,0.0],
|
[1682611200000,355174985,36.6,36.6,28.61,29.52,-8.33,-22.01,27.0,1.1568002446E10,0,0.0],
|
[1685462400000,345031667,29.51,30.1,25.27,25.78,-3.74,-12.67,23.04,9.442101926E9,0,0.0],
|
[1688054400000,1217980960,25.6,42.19,24.75,36.77,10.99,42.63,81.24,4.2515733378E10,0,0.0],
|
[1688572800000,427585117,37.5,47.3,37.06,46.62,9.85,26.79,28.37,1.8368604411E10,0,0.0]]},"error_code":0,"error_description":""}
|
|
*/
|
// 单个股票的 JSON格式处理
|
void RegularInvestment::getOneStock(QByteArray &buffer)
|
{
|
QJsonDocument jd = QJsonDocument::fromJson(buffer);
|
if(jd.isObject()){
|
QJsonObject jObject = jd.object();
|
QJsonArray jArr = jObject.value("data").toObject().value("item").toArray(); // 通过键值对取值
|
int cnt = jArr.count();
|
qDebug()<<"数组size:"<<cnt;
|
QString symbol = jObject.value("data").toObject().value("symbol").toString();
|
QString code = symbol; // 股票代号
|
qDebug()<<"定投:"<<code<<symbol;
|
|
for(int i=0;i<cnt;++i){
|
qint64 timestamp = jArr.at(i).toArray().at(0).toVariant().toLongLong();
|
double close = jArr.at(i).toArray().at(5).toVariant().toDouble();
|
long long volume = jArr.at(i).toArray().at(1).toVariant().toLongLong()/100;
|
|
long long amount = jArr.at(i).toArray().at(9).toVariant().toLongLong()/100000000;
|
QString curDateTime = QDateTime::fromMSecsSinceEpoch(timestamp).toString("yyyy-MM-dd");
|
qDebug()<<curDateTime<<close<<volume<<amount;
|
|
// 处理数据保存到模型中
|
// labels<<"时间"<<"买入价格"<<"数量(手)"<<"所需金额(元)"<<"最新价格"<<"盈亏比"<<"盈亏金额";
|
double lastClose = ui->label_closePrice->text().toDouble();
|
int row = m_model->rowCount();
|
m_model->setRowCount(row+1);
|
m_model->setItem(row,0,new QStandardItem(curDateTime));
|
m_model->setItem(row,1,new QStandardItem(QString::number(close)));
|
m_model->setItem(row,2,new QStandardItem(ui->lineEdit_2->text()));
|
m_model->setItem(row,3,new QStandardItem(QString::number(close * ui->lineEdit_2->text().toInt()*100)));
|
m_model->setItem(row,4,new QStandardItem(ui->label_closePrice->text()));
|
m_model->setItem(row,5,new QStandardItem(QString::number((lastClose-close)/close)));
|
m_model->setItem(row,6,new QStandardItem(QString::number(close * ui->lineEdit_2->text().toInt()*100 *(lastClose-close)/close)));
|
|
|
}
|
}
|
}
|
|
void RegularInvestment::on_pushButton_sum_clicked()
|
{
|
double allBuy = 0;
|
double allWin = 0;
|
for(int i=0;i<m_model->rowCount();++i){
|
allBuy += m_model->item(i,3)->text().toDouble();
|
allWin += m_model->item(i,6)->text().toDouble();
|
}
|
ui->label_buyAll->setText(QString::number(allBuy));
|
ui->label_winAll->setText(QString::number(allWin));
|
ui->label_allRate->setText(QString::number((allWin/allBuy)*100));
|
}
|