在Qt中通过信号和插槽系统传递变量[关闭]
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了在Qt中通过信号和插槽系统传递变量[关闭]相关的知识,希望对你有一定的参考价值。
所以我想通过Qt中的信号和插槽系统传递一个std :: string变量;我在堆上有一个名为RecordTalks的类,当收到来自聊天的消息超过25个符号时,它会发出一个信号。代码如下:
#include "recordtalks.h"
// records chat to files RecordTalks::RecordTalks(QObject *parent) {
}
RecordTalks::~RecordTalks() {
std::cout << "destructor" << "
"; }
void RecordTalks::run(QString data) {
std::cout << ">>> whole data is: " << data.toStdString() << " ------------------
";
std::string text = data.toStdString();
extractNick(text);
extractRoom(text);
//std::cout << "save in recordTalks is: " << save << "
";
if((nick.size()!=0 && room.size()!=0))
{
extractText(data);
pushToVector(removeDigitsAndSpecials(nick), subText);
}
else
return; }
void RecordTalks::run() {
save=false;
save = console.saveNowState();
if(save==true)
{
saveToFile(allTexts, "BOT"); //trigger line saving to file
file.close();
removeDuplicatedNicks();
createNickFiles(nicks_v);
match_nicks_and_allTexts(allTexts);
closeNickFiles();
nicks_v.clear();
nickAndFile_pair_vec.clear();
text.clear();
allTexts.clear();
nick.clear();
room.clear();
subText.clear();
save=false;
}
}
void RecordTalks::extractText(QString &data) {
std::string text = data.toStdString(); // tu zmiana
size_t pos, pos2;
if((pos=text.find("PRIVMSG #"))!=std::string::npos)
{
if((pos2=text.find(":",pos))!=std::string::npos)
{
subText = text.substr(pos2+1, text.size()-(pos2+1) );
if((pos=subText.find("u0001ACTION "))!=std::string::npos)
{
subText = subText.substr(pos+8 , subText.size()-3-(pos+8));
}
else
std::cout << "subText: " << subText << "
";
}
}
else //if nothing to write to log:
{
return ;
}
}
void RecordTalks::extractNick(std::string &text) {
Extract_NickAndRoom e;
QString temp = QString::fromStdString(text);
nick = e.extractNick(temp);
//std::cout << "nick is: " << nick << "
";
}
void RecordTalks::extractRoom(std::string &text) {
Extract_NickAndRoom e;
QString temp = QString::fromStdString(text);
room = e.extractRoom(temp);
//std::cout << "room is: " << room << "
"; }
void RecordTalks::pushToVector(std::string nick, std::string &subText)
//general vector with texts {
if(subText.size()>25 ) //if line of text from irc is bigger than 25 signs
{
std::pair<std::string, std::string> para = std::make_pair(nick, subText);
allTexts.push_back(para); // pair --> vector
emit textUpdateSignal(subText);
std::cout << "EMITTTTTTTTTTTTTTTTTTT " << "
";
//std::cout << ">>> subText: " << subText << " nick: " << nick << " <<<" << "
";
}
if(allTexts.size()==60)
{
saveToFile(allTexts, "BOT"); //trigger line saving to file
file.close();
removeDuplicatedNicks();
createNickFiles(nicks_v);
match_nicks_and_allTexts(allTexts);
closeNickFiles();
nicks_v.clear();
nickAndFile_pair_vec.clear();
text.clear();
allTexts.clear();
nick.clear();
room.clear();
subText.clear();
save=false;
}
}
void RecordTalks::saveToFile( std::vector< std::pair<std::string,
std::string> > &allTexts, std::string nickFileName) {
std::string address = "D:\Qt_workspace\weatherBot\logs\" + nickFileName + ".txt";
file.open(address, std::ios::out | std::ios::app);
for (int i = 0; i < allTexts.size(); ++i)
{
file << allTexts[i].second; //writes text to file, not the nicks
}
}
void RecordTalks::createNickFiles(std::vector<std::string> &nicks_v) {
/* make vector of pair nick and file, so we can identify the file name and then
put text-matching-to-file-nick with file name */
for (int i = 0; i < nicks_v.size(); ++i)
{
std::fstream file2("D:\Qt_workspace\weatherBot\logs\"+ nicks_v[i] + ".txt",
std::ios::out | std::ios::app);
std::pair<std::string, std::fstream> nickAndFile_pair;
nickAndFile_pair = std::make_pair(removeDigitsAndSpecials(nicks_v[i]),
std::move(file2));
nickAndFile_pair_vec.push_back(std::move(nickAndFile_pair));
}
}// nicks_v[i] put inside function removeDigitsAndSpecials(std::string& nick)
void RecordTalks::match_nicks_and_allTexts(std::vector<
std::pair<std::string, std::string> > allTexts) {
for (int i = 0; i < nickAndFile_pair_vec.size(); ++i)
{
for (int j = 0; j < allTexts.size(); ++j)
{
if(nickAndFile_pair_vec[i].first == allTexts[j].first)
{
nickAndFile_pair_vec[i].second << allTexts[j].second;
//nickAndFile_pair_vec[j].second.flush();
}
}
}
std::cout << "allTexts size in match_nicks_and_allTexts is: ";
std::cout << allTexts.size() << "
";
}
void RecordTalks::removeDuplicatedNicks() {
std::vector< std::pair<std::string, std::string> > temp = allTexts;
std::cout << "temp size: " << temp.size() << "
";
for (int i = 0; i < temp.size(); ++i)
{
for (int j = i+1; j < temp.size(); ++j)
{
if(temp[i].first == temp[j].first && i+1< temp.size())
{
temp.erase(temp.begin()+j);
j--;
}
}
}
for (int i = 0; i < temp.size(); ++i)
{
nicks_v.push_back(temp[i].first);
}
std::cout << "nicks_v.size: " << nicks_v.size() << "
";
}
void RecordTalks::closeNickFiles() //closes separate nick files {
for (int i = 0; i < nickAndFile_pair_vec.size(); ++i)
{
nickAndFile_pair_vec[i].second.close();
}
std::cout << "Files closed..." << "
"; }
std::string RecordTalks::removeDigitsAndSpecials(std::string& nick) {
for (int i = 0; i < nick.size(); ++i)
{
if(std::isalpha(nick[i]))
{
}
else if(std::isdigit(nick[i]))
{
nick.erase(nick.begin()+i);
std::cout << "removing: " << nick[i] << "
";
i--;
}
else
{
nick.erase(nick.begin()+i);
std::cout << "removing: " << nick[i] << "
";
i--;
}
}
return nick;
}
然后在另一个类我有连接功能。当我用这种形式写它:
connect(recordTalks, &RecordTalks::textUpdateSignal, this, &Socket::updateDatabaseSLOT);
插槽接收信号。但是当我以这种方式编写函数时:
connect(recordTalks, SIGNAL(textUpdateSign(std::string)), this,
SLOT(updateDatabaseSLOT(std::string)));
插槽没有被解雇。所以我的问题是,原因是什么。在其他情况下,后一版本工作得很好。
插槽看起来像这样:
void Socket::updateDatabaseSLOT(std::string textUpdate)
{
std::cout << "updates text: << textUpdate << "
";
database.push_back(textUpdate);
}
答案
我认为你的连接声明中有拼写错误。 Qt可能会令人沮丧。 SIGNAL(textUpdateSign(std::string )
应该是SIGNAL(textUpdateSignal(std::string )
。
以上是关于在Qt中通过信号和插槽系统传递变量[关闭]的主要内容,如果未能解决你的问题,请参考以下文章
C++ 和 QT4.5 - 传递 const int& 过大?通过引用传递是不是有助于信号/插槽?
如果堆分配的对象被销毁并重新分配指针,Qt 的信号和插槽系统会工作吗?
详解 Qt 线程间共享数据(使用signal/slot传递数据,线程间传递信号会立刻返回,但也可通过connect改变)