QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台

学校小学期大作业是用C++写一个“瞎扯”问答系统,花了几天时间学了一下QT就开始上手了,虽然做的不是很复杂和完善,但是稳定性经过测试还是不错,放出来希望能一起交流学习。

1、四个容器,用户,问题,答案,通知
2、用QT自带的QSqlite数据库实现持久化存储
3、实现登录注册,查看,提问,回答,关注,点赞,搜索等基本功能
4、重点是为了锻炼C++的掌握能力,如虚函数、纯虚函数,继承,重载,容器,全局变量


原题如下

程序一:“瞎扯”问答系统(初级版)(60分,抄袭或被抄袭为0分)
    描述:你需要为“瞎扯”公司设计一个问答系统,构建一个允许用户分享知识的平台。
要求如下:
●   必须用面向对象的方法(继承+多态)实现问答系统的基本功能。
●   系统中只有用户这一种角色。
●   用户可以使用自己的用户名和密码登录系统。
用户进入系统后可以进行如下操作:
1.  查看操作:用户可查看当前所有的提问,提问按发表时间排序,顺序为由新到旧,显示问题列表时至少需显示用户和问题标题,用户选择一个提问后可以查看该提问的详细描述及其下的回答,显示回答列表时至少需要显示回答用户、回答内容以及被赞次数。
2.  提问操作:用户可以在系统中发起提问。
3.  回答操作:用户可以回答提问。
4.  点赞操作:用户可以为回答点赞,被赞的次数要能与回答一同显示。
5.  添加关注操作:用户在查看提问和回答时可以选择添加提问者或回答者为关注,用户可以查看自己关注的用户列表。
6.  注销操作:即退出登录,返回最初界面,供后续用户使用。
●   问题需要有标题和内容两部分,回答只有内容不需要标题,一个问题可以有多个回答。
●   在列表显示时应有分页功能。
●   系统中可能涉及的对象有用户、问题、回答等。
●   有用户类,用户类具有:id、name、password、focuslist等属性(其他属性可根据需求自己定义),且具有以下功能。
1.  添加用户为关注功能
●   有BasicInfo类,BasicInfo类使用抽象类的方式实现,BasicInfo类具有id、创建者id、创建时间、内容等属性(其他属性可根据需求自己定义)
●   BasicInfo类的功能有(定义为虚函数或纯虚函数):
1.  获取属性并格式化输出;
2.  创建问题或答案。
●   BasicInfo子类有问题类和回答类,问题类须有属性title表示问题的标题,回答类须有属性praiseNum表示被赞的次数。
注意事项:
●   本题主要考察对C++面向对象特性的掌握,本题需体现继承、虚函数/纯虚函数、抽象类及容器等概念的使用;
●   所有用户信息,问题信息,答案信息,不强行要求以文本形式存储,可在程序内部自行定义;
●   不强求关闭程序时存储程序内数据状态,即重启程序后一切可以重置;
●   必须使用容器类作为保存数据的内部数据结构,可自行选择合适的容器类;
●   必须使用分离式编译,各个类实现于自身的.h和.cpp文件中;
●   提供字符操作界面,提供图形界面的将适当加分。

程序二:“瞎扯”问答系统(高级版)(40分,抄袭或被抄袭为0分)
描述:在程序一的基础上添加如下功能:
1.  搜索功能(通过函数重载实现)
1)  按标题搜索功能:用户可以输入一个关键词对问题进行搜索,搜索结果为标题包含该关键词的问题,例如,当搜索“C++”时,显示的结果为标题为“nC++m”的问题,n、m为任意字符串,n、m可为空字符串。
2)  按发布时间搜索功能。
2.  查看关注用户的提问和回答功能:用户可以在关注列表中选择自己关注的用户,查看该用户的提问和回答。
■   查看用户提问列表功能可重载查看所有提问列表功能函数
要求如下:
●   必须在程序一的代码基础上修改完成;
●   本题考察对C++面向对象特性的掌握,本题需要体现函数重载、输入/输出流重载、文件操作及异常捕获/处理等概念的使用;
●   采用文本文件或二进制文件来保存所有信息,具体格式可自行定义;
●   为问题、答案等类信息重载流操作符<<和>>,以便从文件中读取和写入信息;
●   必须处理读文件时的异常;
●   提供字符操作界面,提供图形界面的将适当加分。

我自己增加的附加功能

附加功能如下:
1.  查看“粉丝”。你可以关注别人,别人自然也能关注你,因此我给用户类里新加了一个“followedlist”,因此用户也能看到自己的粉丝列表,并且可以通过点击某一项查看用户信息及提问回答列表。
2.  新增消息类。消息类和问题类回答类一样继承自BasicInfo类,消息包括:a.邀请和评论,b.被点赞,c.被关注,d.私信。用户在首页可以点击“通知消息”查看各种通知,并能通过直接点击通知进入想要页面。
3.  邀请回答。在用户查看一个问题时,界面下方会有一个“邀请回答”的按钮,用户可以邀请自己关注了的人,也可以邀请自己的“粉丝”,最后也能邀请其他人。被邀请的人会收到通知。
4.  评论回答。在某个回答下面,用户可以评论当前的这个答案,也可以看到别人发布的评论。被评论的答案作者会收到一条通知告知某人评论了他的答案。
5.  私信功能。在查看某个用户的个人资料界面时,右下方有一个“私信”按钮,可以发一条消息给对方,对方收到私信后双击还能直接回复。
6.  搜索答案和用户。用户在首页搜索框中输入搜索字符点击搜索后会显示搜索到的包含所搜字符的问题,答案,用户。按时间搜索也会显示满足要求的答案和问题

我的一点想法

  1. 定义用户类中 ”focuslist”,”followedlist”,”praiselist”,”answerlist”,”asklist”都是vector容器,保存用户、答案、问题的ID,之后可以根据ID查找对象。定义问题类中还定义了一个answerlist的容器来保存这个问题下的答案的ID,通过ID获取到答案。定义答案类的时候则多定义个questionId来保存它对应问题的ID,以便于在查看某一个人的回答时可以看到问题。而新增的通知类由于要满足四种类型的通知消息,因此只有BasicInfo类中的变量远远不够,应该还得知道发送通知的人,通知的类型问题ID,答案ID,标题等等。
  2. 对于用户的五个容器仅仅用get,set两个函数操作是不太够的,引起各自加了一个处理函数,既能添加成员,又能减少成员。
  3. 由于本次课程设计主要考察容器使用,因此不能依赖数据库查找,所以程序一启动就加载了所有数据,放在一个全局变量容器内。
  4. 在显示问题和答案时,由于要求按时间排序,顺序由新到旧,所有在遍历的时候需要从后往前扫。而又由于要分页,我实现的方法则是在MainWindow这个类中定义了一个迭代器,初始是指向所有问题的最后一个元素,也就是最新的问题,每显示一页迭代器向前移动一定数量。因此实现上一页,首页,尾页功能都只是移动迭代器指向的位置。
  5. 点赞和关注这两个操作我们应该给它限制只能赞一次或者关注一次,而第二次点击应该是取消操作所有每次显示一个答案时都要判断用户是否赞过这个答案,是否关注了答主,显示问题时是否关注题主。
  6. 放弃文件选用数据库。虽然这次程序设计的目的是为了锻炼C++的使用,但是由于考虑以后数据库的使用频率可能会比文件高,所以想自学一些QT操作数据库的知识。代价也是很大的,花了一天时间才把数据库方面的函数写完,由于数据库的不了解,遇到了很多坑。

废话不多说,直接上代码,并非完全满足题目要求,如何我的输入输出重载和异常处理解不是很完善。
代码最后是我的经验教训,希望能够给QT的学习者一些帮助。

完整源码下载:https://github.com/Kwongrf/CHEDAN_Universe_v2


(0)类的定义声明
包括用户类,问题类,回答类,通知类,后三个类继承于同一个抽象类BasicInfo.
user.h

#ifndef USER_H
#define USER_H


#include 
#include 

using namespace std;

class User
{
public:
    User();

    int getId();
    void setId(int id);
    QString getName();
    void setName(QString name);
    QString getPassword();
    void setPassword(QString password);
    int getPraisedNum();
    void setPraisedNum(int n);
    vector<int> getFocusList();
    void setFocusList(vector<int> focuslist);
    void handleFocusList(int id,bool method);
    vector<int> getFollowedList();
    void setFollowedList(vector<int> followedlist);
    void handleFollowedList(int id,bool method);
    vector<int> getPraiseList();
    void setPraiseList(vector<int> praiselist);
    void handlePraiseList(int id,bool method);

    vector<int> getAnswerList();
    void setAnswerList(vector<int> answerlist);
    void handleAnswerList(int id,bool method);
    vector<int> getAskList();
    void setAskList(vector<int>asklist);
    void handleAskList(int id,bool method);


private:
    int id;
    QString name;
    QString password;
    int praisedNum;
    vector<int> focuslist;//只存放id
    vector<int> followedlist;
    vector<int> praiselist;
    vector<int> answerlist;
    vector<int> asklist;

};

#endif // USER_H

user.cpp

#include "user.h"
#include "global.h"
User::User()
{

}
int User::getId()
{
    return this->id;
}

void User::setId(int id)
{
    this->id = id;
}

QString User::getName()
{
    return this->name;
}

void User::setName(QString name)
{
    this->name = name;
}

QString User::getPassword()
{
    return this->password;
}

void User::setPassword(QString password)
{
    this->password = password;
}
int User::getPraisedNum()
{
    return this->praisedNum;
}

void User::setPraisedNum(int n)
{
    this->praisedNum = n;
}

vector<int> User::getFocusList()
{
    return this->focuslist;
}

void User::handleFocusList(int id,bool method)//method = 1 增加,method = 0减少
{
    if(method)
    {
        this->focuslist.push_back(id);
    }
    else
    {
        for(vector<int>::iterator it=this->focuslist.begin();it!=this->focuslist.end();++it)
        {
            if(*it<0 || *it>Users.size())
                break;
            if(*it ==id)
            {
                it=this->focuslist.erase(it);
                break;
            }
        }
    }
}
void User::setFocusList(vector<int> focuslist)
{
    this->focuslist = focuslist;
}

vector<int> User::getFollowedList()
{
    return this->followedlist;
}

void User::handleFollowedList(int id,bool method)//method = 1 增加,method = 0减少
{
    if(method)
    {
        this->followedlist.push_back(id);
    }
    else
    {
        for(vector<int>::iterator it=this->followedlist.begin();it!=this->followedlist.end();++it)
        {
            if(*it<0 || *it>Users.size())
                break;
            if(*it ==id)
             {
                it=this->followedlist.erase(it);
                break;
            }
        }
    }
}
void User::setFollowedList(vector<int> followedlist)
{
    this->followedlist = followedlist;
}

vector<int> User::getPraiseList()
{
    return this->praiselist;
}

void User::setPraiseList(vector<int> praiselist)
{
    this->praiselist = praiselist;
}

void User::handlePraiseList(int id,bool method)
{
    if(method)
    {
        this->praiselist.push_back(id);
        //this->setPraisedNum(this->getPraisedNum()+1);
        qDebug()<<"pushback success";
    }
    else
    {
        for(vector<int>::iterator it=this->praiselist.begin();it!=this->praiselist.end();it++)
        {

            qDebug()<<"handle "<<*it<<"and id"<if(*it ==id)
            {
                it=this->praiselist.erase(it);
                //this->setPraisedNum(this->getPraisedNum()-1);
                qDebug()<<"erase user success";
                break;
            }
            else if(*it > Answers.size()||*it<0)//这里出现一个错就是误以为it要小于用户数量,但是肯定不行
                break;
        }
    }
    qDebug()<<"handlePraiseList";
}
vector<int> User::getAnswerList()
{
    return this->answerlist;
}

void User::setAnswerList(vector<int> answerlist)
{
    this->answerlist = answerlist;
}
void User::handleAnswerList(int id,bool method)
{
    if(method)
    {
        this->answerlist.push_back(id);
        qDebug()<<"add answer success";
    }
    else
    {
        for(vector<int>::iterator it=this->answerlist.begin();it!=this->answerlist.end();++it)
        {

            if(*it == id)
            {
                it=this->answerlist.erase(it);
                qDebug()<<"erase answer success";
                break;
            }
            else if(*it> Answers.size()||*it<0)
                break;
        }
    }
}

vector<int> User::getAskList()
{
    return this->asklist;
}

void User::setAskList(vector<int>asklist)
{
    this->asklist = asklist;
}

void User::handleAskList(int id,bool method)
{
    if(method)
    {
        this->asklist.push_back(id);
        qDebug()<<"add ques success";
    }
    else
    {
        for(vector<int>::iterator it=this->asklist.begin();it!=this->asklist.end();++it)
        {

            if(*it ==id)
            {
                it=this->asklist.erase(it);
                qDebug()<<"erase ques success";
                break;
            }
            else if(*it > Questions.size()||*it<0)
                break;
        }
    }
}

basicInfo.h

#ifndef BASICINFO_H
#define BASICINFO_H

#include 



class BasicInfo
{
public:
    BasicInfo();
    int id;
    int userId;
    QString content;
    QString createtime;

    //virtual void show() = 0;
    virtual void created(int id,int userId,QString content,QString createtime) = 0;

    virtual int getId() = 0;
    virtual int getUserId() = 0;
    virtual QString getContent() = 0;
    virtual QString getTime() = 0;
    virtual void setId(int id) = 0;
    virtual void setUserId(int id) = 0;
    virtual void setContent(QString content) = 0;
    virtual void setTime(QString time) = 0;
};

#endif // BASICINFO_H

basic.cpp

#include "basicinfo.h"

BasicInfo::BasicInfo()//因为是抽象类
{

}

question.h

#ifndef QUESTION_H
#define QUESTION_H
#include "basicinfo.h"
#include 
using namespace std;
class Question :public BasicInfo
{
public:
    Question();


    //void show();
    void created(int id,int userId,QString content,QString createtime);
    int getId();
    int getUserId();
    QString getContent();
    QString getTime();
    vector<int> getAnswerList();
    void setAnswerList(vector<int> answerlist);
    QString getTitle();
    void setTitle(QString title);
    void setId(int id);
    void setUserId(int id);
    void setContent(QString content);
    void setTime(QString time);

    //重载输出运算符
    friend  ostream  &operator<<(ostream &os,const Question &ques);  //声明为友元
    //重载输入运算符
    friend  istream  &operator>>(istream &is,Question &ques);
private:
    vector<int> answerlist;
     QString title;

};

#endif // QUESTION_H

question.cpp

#include "question.h"
class MainWindow;
Question::Question()
{

}


void Question::created(int id,int userId,QString content,QString createtime)
{
    this->setId(id);
    this->setUserId(userId);
    this->setContent(content);
    this->setTime(createtime);
}

int Question::getId()
{
    return this->id;
}

int Question::getUserId()
{
    return this->userId;
}

QString Question::getContent()
{
    return this->content;
}

QString Question::getTime()
{
    return this->createtime;
}
vector<int> Question::getAnswerList()
{
    return this->answerlist;
}
void Question::setAnswerList(vector<int> answerlist)
{
    this->answerlist = answerlist;
}

QString Question::getTitle()
{
    return this->title;
}
void Question::setTitle(QString title)
{
    this->title = title;
}

void Question::setId(int id)
{
    this->id = id;
}

void Question::setUserId(int id)
{
    this->userId = id;
}

void Question::setContent(QString content)
{
    this->content = content;
}

void Question::setTime(QString createtime)
{
    this->createtime = createtime;
}
ostream  &operator<<(ostream &os,const Question &ques)
{
    //这一步很重要
    QByteArray ba1 = ques.content.toLatin1();
    char *contentstr = ba1.data();
    QByteArray ba2 = ques.createtime.toLatin1();
    char *timestr = ba2.data();
    QByteArray ba3 = ques.title.toLatin1();
    char *titlestr = ba3.data();
    //os<
    os<return os;
}

istream  &operator>>(istream &is,Question &ques)
{
    QByteArray ba1 = ques.content.toLatin1();
    char *contentstr = ba1.data();
    QByteArray ba2 = ques.createtime.toLatin1();
    char *timestr = ba2.data();
    QByteArray ba3 = ques.title.toLatin1();
    char *titlestr = ba3.data();
    //is>>ans.getId()>>",">>ans.getUserId()>>",">>ans.getQuestionId()>>",">>ans.getPraisedNum()>>",">>ans.getContent()>>","<
    is>>ques.id>>ques.userId>>titlestr>>contentstr>>timestr;
    //输入判断
    if(!is)
        ques = Question(); //如果失败,默认初始化
    return is;
}

notification.h

#ifndef NOTIFICATION_H
#define NOTIFICATION_H
#include "basicinfo.h"

#include 

enum Type{Notice=1,Praise=2,Focused=3,Message=4};

class Notification :public BasicInfo
{
public:
    Notification();


    int getSenderId();
    Type getType();
    QString getTitle();
    int getQuestionId();
    int getAnswerId();
    void created(int id,int userId,QString content,QString createtime);
    int getId();
    int getUserId();

    QString getContent();
    QString getTime();
    void setId(int id);
    void setUserId(int id);

    void setContent(QString content);
    void setTime(QString time);
    void setTitle(QString title);
    void setSenderId(int id);
    void setType(int type);
    void setQuestionId(int id);
    void setAnswerId(int id);

private:

    int senderId;//谁发的
    int questionId;//邀请回答时的情况
    int answerId;//查看评论或点赞时
    QString title;
    Type type;




};

#endif // NOTIFICATION_H

notification.cpp

#include "notification.h"

Notification::Notification()
{

}
int Notification::getId()
{
    return this->id;
}

int Notification::getUserId()
{
    return this->userId;
}

QString Notification::getContent()
{
    return this->content;
}

QString Notification::getTime()
{
    return this->createtime;
}
int Notification::getSenderId()
{
    return this->senderId;
}
QString Notification::getTitle()
{
    return this->title;
}
Type Notification::getType()
{
    return this->type;
}
void Notification::setSenderId(int id)
{
    this->senderId = id;
}
void Notification::setTitle(QString title)
{
    this->title = title;
}
void Notification::setType(int type)
{

        this->type = Type(type);
}

void Notification::setId(int id)
{
    this->id = id;
}

void Notification::setUserId(int id)
{
    this->userId = id;
}

void Notification::setContent(QString content)
{
    this->content = content;
}

void Notification::setTime(QString createtime)
{
    this->createtime = createtime;
}
void Notification::created(int id,int userId,QString content,QString createtime)//因为没有实现这个函数导致出现vtable reference
{
    this->setId(id);
    this->setUserId(userId);
    this->setContent(content);
    this->setTime(createtime);
}
int Notification::getQuestionId()
{
    return this->questionId;
}
int Notification::getAnswerId()
{
    return this->answerId;
}
void Notification::setQuestionId(int id)
{
    this->questionId=id;
}
void Notification::setAnswerId(int id)
{
    this->answerId=id;
}

(0.5)全局变量以及数据库
QT实现全局变量的方法有两个,一个是 extern ,一个是定义一个类来放所以的全局变量,变量声明前加static。我这里用的是使用Global类来放全局函数,用extern来声明全局变量容器,两种方法都使用。
database.h

#ifndef DATABASE_H
#define DATABASE_H
#include "user.h"
#include "question.h"
#include "answer.h"
#include "notification.h"
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
class Database
{
public:
    bool createConnection();                   //创建一个连接
    bool createTable();                    //创建4张数据库表

    bool insert(User user);                 //插入数据
    bool insert(Question ques);             //出入数据
    bool insert(Answer ans);                //出入数据
    bool insert(Notification notif);

    bool queryById(const int id,User& user);     //查询用户信息
    bool queryById(const int id,Question& ques);            //查询问题信息
    bool queryById(const int id,Answer& ans);            //查询问题信息

    vector queryAllUser();
    vector queryAllQues();
    vector queryAllAns();
    vector queryAllAns(vector<int> ids);
    vector queryAllNotif();

    bool update(User user);   //更新
    bool update(Question ques);   //更新
    bool update(Answer ans);   //更新
    //bool deleteById(int id);   //删除
    //bool sortById();           //排序
};

#endif // DATABASE_H

database.cpp

#include "database.h"
#include "user.h"
#include 
#include 


string vectostr(vector<int>list);
vector<int> split(QString& str,const char* c);

//建立一个数据库连接
bool Database::createConnection()
{

    //以后就可以用"sqlite1"与数据库进行连接了
    QSqlDatabase db = QSqlDatabase::addDatabase("QSQLITE","sqlite1");
    db.setDatabaseName(".//CHEDAN_Universe.db");
    if( !db.open())
    {   QSqlQuery query(db);
        QSqlError lastError = query.lastError();
        qDebug() << lastError.driverText() << QString(QObject::tr("无法建立数据库连接"));
        return false;
    }
    qDebug() << QString(QObject::tr("建立数据库连接"));
    return true;
}
//创建数据库表
bool Database::createTable()
{

    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    bool success1 = query.exec("create table users(id int primary key,name varchar(30),userpassword varchar(30),praisedNum int,answerlist varchar(100),asklist varchar(100),focuslist varchar(100),followedlist varchar(100),praiselist varchar(100))");
    if(success1)
    {
        qDebug() << QObject::tr("数据库表1创建成功!\n");

    }
    else
    {
        QSqlError lastError = query.lastError();
        qDebug() << lastError.driverText() << QString(QObject::tr("创建数据库表1失败"));

    }
    bool success2 = query.exec("create table questions(id int primary key,title varchar(100),userId int,"
                              "content varchar(200),createtime varchar(40),answerlist varchar(100))");
    if(success2)
    {
        qDebug() << QObject::tr("数据库表2创建成功!\n");

    }
    else
    {
        QSqlError lastError = query.lastError();
        qDebug() << lastError.driverText() << QString(QObject::tr("创建数据库表2失败"));

    }
    bool success3 = query.exec("create table answers(id int primary key,userId int,questionId int,"
                              "praisedNum int,content varchar(200),createtime varchar(40))");
    if(success3)
    {
        qDebug() << QObject::tr("数据库表3创建成功!\n");

    }
    else
    {
        QSqlError lastError = query.lastError();
        qDebug() << lastError.driverText() << QString(QObject::tr("创建数据库表3失败"));

    }
    bool success4 = query.exec("create table notifications(id int primary key,userId int,senderId int,noticetype int,"
                              "title varchar(100),content varchar(200),createtime varchar(40),questionId int, answerId int)");
    if(success4)
    {
        qDebug() << QObject::tr("数据库表4创建成功!\n");

    }
    else
    {
        QSqlError lastError = query.lastError();
        qDebug() << lastError.driverText() << QString(QObject::tr("创建数据库表4失败"));
        return false;
    }
    return true;
}

//向数据库中插入记录,即注册账号信息
bool Database::insert(User user)
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接

    QSqlQuery query(db);
    query.prepare("insert into users values(?, ?, ?, ?, ?, ?, ?, ?, ?)");
    query.bindValue(0, user.getId());
    query.bindValue(1, user.getName());
    query.bindValue(2, user.getPassword());
    query.bindValue(3, user.getPraisedNum());
    string answerliststr = vectostr(user.getAnswerList());
    query.bindValue(4,answerliststr.c_str());

    string askliststr = vectostr(user.getAskList());
    query.bindValue(5,askliststr.c_str());
    //将vector转化成一个字符串存起来
    string focusliststr = vectostr(user.getFocusList());
    query.bindValue(6, focusliststr.c_str());
    //将vector转化成一个字符串存起来
    string followedliststr = vectostr(user.getFollowedList());
    query.bindValue(7,followedliststr.c_str());

    string praiseliststr = vectostr(user.getPraiseList());
    query.bindValue(8,praiseliststr.c_str());


    bool success=query.exec();
    if(!success)
    {
          QSqlError lastError = query.lastError();
          qDebug() << lastError.driverText() << QString(QObject::tr("插入失败"));
          return false;
    }
    return true;
}

bool Database::insert(Question ques)
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    query.prepare("insert into questions values(?, ?, ?, ?, ?, ?)");
    query.bindValue(0, ques.getId());
    query.bindValue(1, ques.getTitle());
    query.bindValue(2, ques.getUserId());
    query.bindValue(3, ques.getContent());
    query.bindValue(4, ques.getTime());
    //将vector转化成一个字符串存起来
    string answerliststr = vectostr(ques.getAnswerList());
    query.bindValue(5,answerliststr.c_str());

    bool success=query.exec();
    if(!success)
    {
          QSqlError lastError = query.lastError();
          qDebug() << lastError.driverText() << QString(QObject::tr("插入失败"));
          return false;
    }
    return true;
}

bool Database::insert(Answer ans)
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    query.prepare("insert into answers values(?, ?, ?, ?, ?, ?)");
    query.bindValue(0, ans.getId());
    query.bindValue(1, ans.getUserId());
    query.bindValue(2, ans.getQuestionId());
    query.bindValue(3, ans.getPraisedNum());
    query.bindValue(4, ans.getContent());
    query.bindValue(5, ans.getTime());


    bool success=query.exec();
    if(!success)
    {
          QSqlError lastError = query.lastError();
          qDebug() << lastError.driverText() << QString(QObject::tr("插入失败"));
          return false;
    }
    return true;
}
bool Database::insert(Notification notif)
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    query.prepare("insert into notifications values(?, ?, ?, ?, ?, ?, ?, ?, ?)");
    query.bindValue(0, notif.getId());
    query.bindValue(1, notif.getUserId());
    query.bindValue(2, notif.getSenderId());
    query.bindValue(3, notif.getType());
    query.bindValue(4, notif.getTitle());
    query.bindValue(5, notif.getContent());
    query.bindValue(6, notif.getTime());
    query.bindValue(7, notif.getQuestionId());
    query.bindValue(8, notif.getAnswerId());

    bool success=query.exec();
    if(!success)
    {
          QSqlError lastError = query.lastError();
          qDebug() << lastError.driverText() << QString(QObject::tr("插入失败"));
          return false;
    }
    return true;
}

//查询某个用户信息
bool Database::queryById(const int id,User& user)
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    /*QSqlTableModel model;
    model.setTable("users");
    model.setEditStrategy(QSqlTableModel::OnManualSubmit);
    char* idstr = itoa(id,idstr,10);
    //model->setFilter(QObject::tr("id = %1").arg(idstr));
    model.setFilter("id = 1");
    if(model.select())
    {
        const char* c = ",";
        QSqlRecord record = model.record(0);
        user.setId(record.value("id").toInt());
        user.setName(record.value("name").toString());
        user.setPassword(record.value("password").toString());
        user.setPraisedNum(record.value("praisedNum").toInt());
        user.setAnswerNum(record.value("answerNum").toInt());
        user.setAskNum(record.value("askNum").toInt());
        QString focusstr = record.value("focuslist").toString();
        vectorfocuslist = split(focusstr,c);
        user.setFocusList(focuslist);
        QString followedstr = record.value("followedlist").toString();
        user.setFollowedList(split(followedstr,c));
        return true;
    }
    else
    {

        return false;
    }*/
    QSqlQuery query(db);
    bool success = query.exec(QString("select * from users where id = %1").arg(id));
    //bool success = query.exec("select * from users where id = 1");
    qDebug()<< " "<if(success)
    {

       if(query.next())
        {
           for(int index = 0; index < 7; index++)
               qDebug() << query.value(index) << " ";
           qDebug() << "\n";
            const char* c = ",";
            user.setId(id);
            user.setName(query.value(1).toString());
            user.setPassword(query.value(2).toString());
            user.setPraisedNum(query.value(3).toInt());
            QString answerstr = query.value(4).toString();
            user.setAnswerList(split(answerstr,c));
            QString askstr = query.value(5).toString();
            user.setAnswerList(split(askstr,c));
            QString focusstr = query.value(6).toString();
            vector<int>focuslist = split(focusstr,c);
            user.setFocusList(focuslist);
            QString followedstr = query.value(7).toString();
            user.setFollowedList(split(followedstr,c));
            QString praisestr = query.value(8).toString();
            user.setPraiseList(split(praisestr,c));


            qDebug()<2).toString();
            return true;
        }
        else
           return false;

    }
    else
    {
        qDebug()<return false;
    }
}
bool Database::queryById(const int id,Question& ques)            //查询问题信息
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    bool success = query.exec(QString("select * from questions where id = %1").arg(id));
    qDebug()<< " "<if(success)
    {

       if(query.next())
        {
            const char* c = ",";
            ques.setId(id);
            ques.setTitle(query.value(1).toString());
            ques.setUserId(query.value(2).toInt());
            ques.setContent(query.value(3).toString());
            ques.setTime(query.value(4).toString());

            QString answerstr = query.value(5).toString();
            vector<int>answerlist = split(answerstr,c);
            ques.setAnswerList(answerlist);

            return true;
        }
        else
           return false;

    }
    else
    {
        qDebug()<return false;
    }
}

bool Database::queryById(const int id,Answer& ans)            //查询问题信息
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    bool success = query.exec(QString("select * from answers where id = %1").arg(id));
    qDebug()<< " "<if(success)
    {

       if(query.next())
        {
            ans.setId(id);
            ans.setUserId(query.value(1).toInt());
            ans.setQuestionId(query.value(2).toInt());
            ans.setPraisedNum(query.value(3).toInt());
            ans.setContent(query.value(4).toString());
            ans.setTime(query.value(5).toString());

            return true;
        }
        else
           return false;

    }
    else
    {
        qDebug()<return false;
    }
}
vector Database::queryAllQues()                         //返回所有问题
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    bool success = query.exec("select * from questions");
    qDebug()<< " "<if(success)
    {
        vector questions;
        while(query.next())
        {
            Question ques;
            const char* c = ",";
            ques.setId(query.value(0).toInt());
            ques.setTitle(query.value(1).toString());
            ques.setUserId(query.value(2).toInt());
            ques.setContent(query.value(3).toString());
            ques.setTime(query.value(4).toString());

            QString answerstr = query.value(5).toString();
            vector<int>answerlist = split(answerstr,c);
            ques.setAnswerList(answerlist);
            questions.push_back(ques);

        }
        return questions;

    }
    else
    {
        qDebug()<vector Database::queryAllAns()
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    bool success = query.exec("select * from answers");
    qDebug()<< " "<if(success)
    {
        vector answers;
        while(query.next())
        {
            Answer ans;
            ans.setId(query.value(0).toInt());
            ans.setUserId(query.value(1).toInt());
            ans.setQuestionId(query.value(2).toInt());
            ans.setPraisedNum(query.value(3).toInt());
            ans.setContent(query.value(4).toString());
            ans.setTime(query.value(5).toString());

            answers.push_back(ans);

        }
        return answers;
    }
}
vector Database::queryAllUser()
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    bool success = query.exec("select * from users");
    qDebug()<< " "<if(success)
    {
        vector users;
        while(query.next())
        {
            User user;
            const char* c = ",";
            user.setId(query.value(0).toInt());
            user.setName(query.value(1).toString());
            user.setPassword(query.value(2).toString());
            user.setPraisedNum(query.value(3).toInt());
            QString answerstr = query.value(4).toString();
            user.setAnswerList(split(answerstr,c));
            QString askstr = query.value(5).toString();
            user.setAskList(split(askstr,c));
            QString focusstr = query.value(6).toString();
            vector<int>focuslist = split(focusstr,c);
            user.setFocusList(focuslist);
            QString followedstr = query.value(7).toString();
            user.setFollowedList(split(followedstr,c));
            QString praisestr = query.value(8).toString();
            user.setPraiseList(split(praisestr,c));

            users.push_back(user);

        }
        return users;
    }
}

vector Database::queryAllAns(vector<int> ids)
{
    Answer ans;
    vector answers;
    for (vector<int>::iterator it = ids.begin();it!=ids.end();++it)
    {
        queryById(*it,ans);
        answers.push_back(ans);
    }
    return answers;

}
bool Database::update(User user)   //更新
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    query.prepare(QString("update users set id=?,name=?,"
                             "userpassword=?, praisedNum=?,"                           
                             "answerlist=?, asklist=?,"
                             "focuslist=?, followedlist=?,"
                             "praiselist=? where id = %1").arg(user.getId()));

    query.bindValue(0, user.getId());
    query.bindValue(1, user.getName());
    query.bindValue(2, user.getPassword());
    query.bindValue(3, user.getPraisedNum());
    string answerliststr = vectostr(user.getAnswerList());
    query.bindValue(4,answerliststr.c_str());

    string askliststr = vectostr(user.getAskList());
    query.bindValue(5,askliststr.c_str());
    //将vector转化成一个字符串存起来
    string focusliststr = vectostr(user.getFocusList());
    query.bindValue(6, focusliststr.c_str());
    //将vector转化成一个字符串存起来
    string followedliststr = vectostr(user.getFollowedList());
    query.bindValue(7,followedliststr.c_str());

    string praiseliststr = vectostr(user.getPraiseList());
    query.bindValue(8,praiseliststr.c_str());

    bool success=query.exec();
    if(!success)
    {
          QSqlError lastError = query.lastError();
          qDebug() << lastError.driverText() << QString(QObject::tr("user更新失败"));
          return false;
    }
    return true;
}
vector Database::queryAllNotif()
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    bool success = query.exec("select * from notifications");
    qDebug()<< " "<if(success)
    {
        vector notifications;
        while(query.next())
        {
            Notification notif;
            notif.setId(query.value(0).toInt());
            notif.setUserId(query.value(1).toInt());
            notif.setSenderId(query.value(2).toInt());
            notif.setType(query.value(3).toInt());
            notif.setTitle(query.value(4).toString());
            notif.setContent(query.value(5).toString());
            notif.setTime(query.value(6).toString());
            notif.setQuestionId(query.value(7).toInt());
            notif.setAnswerId(query.value(8).toInt());
            notifications.push_back(notif);

        }
        return notifications;
    }
}

bool Database::update(Question ques)   //更新
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    query.prepare(QString("update questions set id=?,title=?,"
                             "userId=?, content=?,"
                             "createtime=?, answerlist=?"
                             " where id=%1").arg(ques.getId()));
    //qDebug()<
    query.bindValue(0, ques.getId());
    query.bindValue(1, ques.getTitle());
    query.bindValue(2, ques.getUserId());
    query.bindValue(3, ques.getContent());
    query.bindValue(4, ques.getTime());
    //将vector转化成一个字符串存起来
    string answerliststr = vectostr(ques.getAnswerList());
    query.bindValue(5,answerliststr.c_str());

    bool success=query.exec();
    if(!success)
    {
          QSqlError lastError = query.lastError();
          qDebug() << lastError.driverText() << QString(QObject::tr("qustion更新失败"));
          return false;
    }
    return true;
}
bool Database::update(Answer ans)
{
    QSqlDatabase db = QSqlDatabase::database("sqlite1"); //建立数据库连接
    QSqlQuery query(db);
    query.prepare(QString("update answers set id=?,userId=?,"
                             "questionId=?,praisedNum=?,content=?,"
                             "createtime=? where id=%1").arg(ans.getId()));
    //qDebug()<
    query.bindValue(0, ans.getId());
    query.bindValue(1, ans.getUserId());
    query.bindValue(2, ans.getQuestionId());
    query.bindValue(3, ans.getPraisedNum());
    query.bindValue(4, ans.getContent());
    query.bindValue(5, ans.getTime());

    bool success=query.exec();
    if(!success)
    {
          QSqlError lastError = query.lastError();
          qDebug() << lastError.driverText() << QString(QObject::tr("answer更新失败"));
          return false;
    }
    return true;
}


string vectostr(vector<int>list)
{
    string liststr="";
    string str="";
    char* cstr;
    for(vector<int>::iterator it=list.begin();it!=list.end();++it)
    {
        itoa(*it,cstr,10);
        str = cstr;
        liststr =liststr+str;
        if (it!=list.end()-1)
            liststr =liststr+",";
    }
    return liststr;
}

vector<int> split(QString& str,const char* c)
{
    char *cstr, *p;
    vector<int> res;
    //cstr = new char[str.size()+1];
    //strcpy(cstr,str.c_str());
    QByteArray ba = str.toLatin1();
    cstr = ba.data();
    p = strtok(cstr,c);
    //qDebug()<<"split"<
    while(p!=NULL)
    {
        res.push_back(atoi(p));
        p = strtok(NULL,c);
        //qDebug()<<"split"<
    }
    return res;
}

global.h

#ifndef GLOBAL_H
#define GLOBAL_H

#include "database.h"
#include 
using namespace std;


class Global
{
public:
    Global();
    static User getUser(int id);
    static Question getQuestion(int id);
    static Answer getAnswer(int id);
    static Notification getNotification(int id);

    static void update(User user);
    static void update(Question ques);
    static void update(Answer ans);

    static void insert(User user);
    static void insert(Question ques);
    static void insert(Answer ans);
    static void insert(Notification notif);

};

extern Database Db;
extern User USER;
extern vector Questions;
extern vector Answers;
extern vector Users;
extern vector Notifications;
#endif // GLOBAL_H

global.cpp

#include "global.h"

/*Global::Global()
{

}*/
Database Db;
User USER;
vector Questions;
vector Answers;
vector Users;
vector Notifications;
User Global::getUser(int id)
{
    User user;
    vector::iterator it;
    for(it = Users.begin();it!=Users.end();++it)
    {
        user = *it;
        if(user.getId()==id)
            break;
    }
    if(it!=Users.end())
        return user;
    else
    {
        user.setId(-1);
        return user;
    }
}

Question Global::getQuestion(int id)
{
    Question ques;
    for(vector::iterator it = Questions.begin();it!=Questions.end();++it)
    {
        ques = *it;
        if(ques.getId()==id)
            break;
    }
    return ques;
}

Answer Global::getAnswer(int id)
{
    Answer ans;
    for(vector::iterator it = Answers.begin();it!=Answers.end();++it)
    {
       ans = *it;
        if(ans.getId()==id)
               break;
    }
    return ans;
}
Notification Global::getNotification(int id)
{
    Notification notif;
    for(vector::iterator it = Notifications.begin();it!=Notifications.end();++it)
    {
       notif = *it;
        if(notif.getId()==id)
               break;
    }
    return notif;
}

void Global::update(User user)
{
    try{
        for(vector::iterator it = Users.begin();it!=Users.end();++it)
        {

            if((*it).getId()==user.getId())
            {
                (*it).setName(user.getName());
                (*it).setPassword(user.getPassword());
                (*it).setAnswerList(user.getAnswerList());
                (*it).setAskList(user.getAskList());
                (*it).setFollowedList(user.getFollowedList());
                (*it).setPraiseList(user.getPraiseList());
            }
        }
    Db.update(user);
    }
    catch(...)
    {
        qDebug()<<"update user error";
    }
    qDebug()<<"update user success";

}

void Global::update(Question ques)
{
    try{
        for(vector::iterator it = Questions.begin();it!=Questions.end();++it)
        {

            if((*it).getId()==ques.getId())
            {
                (*it).setTitle(ques.getTitle());
                (*it).setAnswerList(ques.getAnswerList());
                (*it).setContent(ques.getContent());
            }
        }
        Db.update(ques);
    }
    catch(...)
    {
        qDebug()<<"update question error";
    }
}

void Global::update(Answer ans)
{
    for(vector::iterator it = Answers.begin();it!=Answers.end();++it)
    {

        if((*it).getId()==ans.getId())
        {

            (*it).setPraisedNum(ans.getPraisedNum());
            (*it).setContent(ans.getContent());
        }
    }
    Db.update(ans);
}

void Global::insert(User user)
{
    Users.push_back(user);
    Db.insert(user);
}

void Global::insert(Question ques)
{
   Questions.push_back(ques);
    Db.insert(ques);
}

void Global::insert(Answer ans)
{
    Answers.push_back(ans);
    Db.insert(ans);
}
void Global::insert(Notification notif)
{
    Notifications.push_back(notif);
    Db.insert(notif);
}

(1)主函数
main.cpp

#include "mainwindow.h"
#include 
#include 
#include 
#include 
#include "signin.h"
#include "global.h"
#include 
int main(int argc, char *argv[])
{

    QApplication a(argc, argv);
    MainWindow w;
    try{
        Db.createConnection();
        Db.createTable();
        Questions = Db.queryAllQues();
        Answers = Db.queryAllAns();
        Users = Db.queryAllUser();
        Notifications = Db.queryAllNotif();
    }
    catch(...)
    {
        qDebug()<<"loading datas error";

    }


    for(vector::iterator it= Answers.begin();it!=Answers.end();++it)
    {
        Answer a= *it;
        qDebug()<" "<for(vector::iterator it= Questions.begin();it!=Questions.end();++it)
    {
        Question a= *it;
        qDebug()<" "<for(vector::iterator it= Users.begin();it!=Users.end();++it)
    {
        User a= *it;
        qDebug()<" "<".//image/1.gif");
    QSplashScreen splash(pixmap);
    splash.setWindowOpacity(0.7);// 设置窗口透明度
    QLabel label(&splash);
    QMovie mv(".//image/1.gif");
    label.setMovie(&mv);
    mv.start();
    splash.show();
    splash.setCursor(Qt::BlankCursor);

    for(int i=0; i<10000; i+=mv.speed())
    {
        QCoreApplication::processEvents();

        Sleep(mv.speed());

    }
    SignIn signInDlg;
    splash.finish(&signInDlg);
    signInDlg.setAutoFillBackground(true);
    QPalette p_signin;
    QPixmap pixmap_signin(".//image/594_492.png");
    p_signin.setBrush(QPalette::Window, QBrush(pixmap_signin));
    signInDlg.setPalette(p_signin);
    if(signInDlg.exec() == QDialog::Accepted)
    {

        w.setAutoFillBackground(true);
        QPalette palette;
        QPixmap pixmap(".//image/bg.jpg");
        palette.setBrush(QPalette::Window, QBrush(pixmap));
        w.setPalette(palette);
        w.show();

        w.showQuestions();
        qDebug()<<"ok";
        return a.exec();
    }
    else     
        return 0;

}

(2)登录
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第1张图片
signin.h

#ifndef SIGNIN_H
#define SIGNIN_H

#include 

namespace Ui {
class SignIn;
}

class SignIn : public QDialog
{
    Q_OBJECT

public:
    explicit SignIn(QWidget *parent = 0);
    ~SignIn();

private slots:
    void on_signInButton_clicked();

    void on_signUpButton_clicked();

private:
    Ui::SignIn *ui;
};

#endif // SIGNIN_H

signin.cpp

#include "signin.h"
#include "ui_signin.h"
#include "user.h"
#include "global.h"
#include 
#include "signup.h"
SignIn::SignIn(QWidget *parent) :
    QDialog(parent),
    ui(new Ui::SignIn)
{
    ui->setupUi(this);
    this->resize(594,492);
    this->setFixedSize(594,492);
    ui->lineEdit_2->setEchoMode(QLineEdit::Password);
}

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

void SignIn::on_signInButton_clicked()
{
    User user;
    QString CurrentId = ui->lineEdit->text();
    QString CurrentPassWord = ui->lineEdit_2->text();
    bool* ok = NULL;
    int idInt = CurrentId.toInt(ok,10);
    qDebug()<<"idInt"<Global::getUser(idInt);
    if(user.getId()!=-1)
    {
        if(user.getPassword()==CurrentPassWord)
        {

            accept();
            USER = user;
            qDebug()<<"USER.getId()"<<USER.getId();
            return;
        }
        else
        {
            ui->lineEdit_2->clear();
            QMessageBox fail(QMessageBox::NoIcon, "失败", "密码错误");
            fail.addButton("确定", QMessageBox::AcceptRole);
            fail.exec();
        }
    }
    else
    {
        ui->lineEdit->clear();
        ui->lineEdit_2->clear();
        QMessageBox fail(QMessageBox::NoIcon, "失败", "账户不存在");
        fail.addButton("确定", QMessageBox::AcceptRole);
        fail.exec();
    }
}

void SignIn::on_signUpButton_clicked()
{
    SignUp signUpDlg;
    signUpDlg.setAutoFillBackground(true);
    QPalette palette;
    QPixmap pixmap(".//image/527_511.png");
    palette.setBrush(QPalette::Window, QBrush(pixmap));
    signUpDlg.setPalette(palette);
    signUpDlg.exec();
}

(3)注册
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第2张图片
signup.h

#ifndef SIGNUP_H
#define SIGNUP_H

#include 

namespace Ui {
class SignUp;
}

class SignUp : public QDialog
{
    Q_OBJECT

public:
    explicit SignUp(QWidget *parent = 0);
    ~SignUp();

private slots:
    void on_buttonBox_accepted();

    void on_buttonBox_rejected();

private:
    Ui::SignUp *ui;
};

#endif // SIGNUP_H

signup.cpp

#include "signup.h"
#include "ui_signup.h"
#include "global.h"

#include 
SignUp::SignUp(QWidget *parent) :
    QDialog(parent),
    ui(new Ui::SignUp)
{
    ui->setupUi(this);
    this->resize(527,511);
    ui->lineEdit_2->setEchoMode(QLineEdit::Password);
    ui->lineEdit_3->setEchoMode(QLineEdit::Password);
}

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

void SignUp::on_buttonBox_accepted()
{
    QString id = ui->lineEdit->text();
    QString password = ui->lineEdit_2->text();
    QString cfpassword = ui->lineEdit_3->text();
    QString name = ui->lineEdit_4->text();
    bool* ok = NULL;
    User user=Global::getUser(id.toInt(ok,10));
    if(user.getId()!=-1)
    {
        QMessageBox fail(QMessageBox::NoIcon, "失败", "该账号已存在");
        ui->lineEdit->clear();
        fail.addButton("确定", QMessageBox::AcceptRole);
        fail.exec();
    }
    else if(password == cfpassword)
    {
        user.setId(id.toInt());
        user.setPassword(password);
        user.setName(name);
        user.setPraisedNum(0);
        vector ls;
        user.setFocusList(ls);
        user.setFollowedList(ls);
        user.setPraiseList(ls);
        user.setAnswerList(ls);
        user.setAskList(ls);
        Global::insert(user);
        this->close();

    }
    else
    {
        QMessageBox fail(QMessageBox::NoIcon, "失败", "两次密码不一致");
        ui->lineEdit_2->clear();
        ui->lineEdit_3->clear();
        fail.addButton("确定", QMessageBox::AcceptRole);
        fail.exec();
    }
}



void SignUp::on_buttonBox_rejected()
{
    this->close();
}

(3)主窗口
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第3张图片
mainwindow.h

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include 
#include "question.h"
#include "global.h"
#include "quesanswindow.h"
#include "ask.h"
#include "userdatawindow.h"
#include 
using namespace std;
namespace Ui {
class MainWindow;
}

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    explicit MainWindow(QWidget *parent = 0);
    ~MainWindow();
    void showQuestions();

private slots:
    void on_askQuesButton_clicked();

    void on_tableWidget_doubleClicked(const QModelIndex &index);

    void on_searchButton_clicked();

    void on_userDataButton_clicked();

    void on_freshButton_clicked();

    void on_signoutButton_clicked();

    void on_focusButton_clicked();

    void on_homepageButton_clicked();

    void on_lastpageButton_clicked();

    void on_nextpageButton_clicked();

    void on_endpageButton_clicked();

    void on_gotopageButton_clicked();

    void on_searchButton_2_clicked();

    void on_followedButton_clicked();

    void on_noticeButton_clicked();

private:
    Ui::MainWindow *ui;
    vector::reverse_iterator qrit;
    int page;
};

#endif // MAINWINDOW_H

mainwindow.cpp

#include "mainwindow.h"
#include "ui_mainwindow.h"
#include "global.h"
#include "question.h"
#include "quesanswindow.h"
#include "ask.h"
#include "userdatawindow.h"
#include "signin.h"
#include "focuswindow.h"
#include "searchresult.h"
#include "noticewindow.h"
#include 
#include 
using namespace std;

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    this->resize(1140,640);
    this->setFixedSize(1140,640);

    ui->dateEdit->setDate(QDate::currentDate());
}

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


void MainWindow::showQuestions()
{
    ui->tableWidget->setRowCount(0);
    ui->tableWidget->setColumnCount(5);
    ui->tableWidget->verticalHeader()->setDefaultSectionSize(40);
    ui->tableWidget->setFont(QFont("微软雅黑", 10, QFont::Bold ));

    ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);
    QStringList header;
    header<"ID")<"问题")<"题主")<"回答数")<"时间");
    ui->tableWidget->setHorizontalHeaderLabels(header);
    ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
    ui->tableWidget->setShowGrid(false);
    ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
    ui->tableWidget->setStyleSheet("background-color:rgba(0,0,0,30)");
    ui->tableWidget->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    //ui->tableWidget->show();

    //vector<Question> questions = Db.queryAllQues();
//    int flag=0;
//    int row = 0;
//    for(vector<Question>::reverse_iterator rit = Questions.rbegin();rit!=Questions.rend();++rit)
//    {
//        Question ques = *rit;
//        ui->tableWidget->setRowCount(row+1);
//        ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(ques.getId())));
//        ui->tableWidget->setItem(row,1,new QTableWidgetItem(ques.getTitle()));
//        ui->tableWidget->setItem(row,2,new QTableWidgetItem(Global::getUser(ques.getUserId()).getName()));
//        ui->tableWidget->setItem(row,3,new QTableWidgetItem(QString::number(ques.getAnswerList().size())));
//        ui->tableWidget->setItem(row,4,new QTableWidgetItem(ques.getTime()));

//        //qDebug()<<QString::number(ques.getId())<<" "<" "<" "<1;
//    }

//    for(int row = 0;row < Questions.size();row++)
//    {
//        for(int col = 0;col<5;col++)
//            ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
//    }

//    if(flag==0)
//         ui->tableWidget->setRowCount(0);
//    ui->tableWidget->show();

    //实现分页
   this->on_homepageButton_clicked();

    int max = Questions.size()/10+1;
    int min = 1;
    //设置QLineEdit只能输入数字
    QIntValidator* validator = new QIntValidator(min,max,this);
    ui->pageNum->setValidator(validator);

}




void MainWindow::on_askQuesButton_clicked()
{
    Ask askDlg;
    askDlg.setAutoFillBackground(true);
    QPalette palette;
    QPixmap pixmap(".//image/bg3.jpg");
    palette.setBrush(QPalette::Window, QBrush(pixmap));
    askDlg.setPalette(palette);
    if(askDlg.exec() ==  QDialog::Accepted)
    {
        this->showQuestions();
    }
}


void MainWindow::on_tableWidget_doubleClicked(const QModelIndex &index)
{
    bool* ok = NULL;
    int id =ui->tableWidget->item(index.row(),0)->text().toInt(ok,10);

    QuesAnsWindow *quesansWindow = new QuesAnsWindow;

    quesansWindow->show();
    quesansWindow->showQuesAnswers(id);
}

void MainWindow::on_searchButton_clicked()
{
    QString searchStr = ui->searchEdit->text();
    if(searchStr!="")
    {
        SearchResult *sr = new SearchResult;
        sr->search(searchStr);
        sr->exec();
    }
    else
    {
        QMessageBox fail(QMessageBox::NoIcon, "失败", "请输入搜索内容");
        fail.addButton("确定", QMessageBox::AcceptRole);
        fail.exec();
    }


}
void MainWindow::on_searchButton_2_clicked()
{
    QDate date = ui->dateEdit->date();
    //QDateTime t = QDateTime::fromString(searchStr,"yyyy-MM-dd");
    SearchResult *sr = new SearchResult;
    sr->search(date);
    sr->exec();
}

void MainWindow::on_userDataButton_clicked()
{
    UserdataWindow userdataWindow;//实际上是Dialog

    USER = Global::getUser(USER.getId());//更新USER
    userdataWindow.setUserId(USER.getId());
    userdataWindow.showAllDatas();
    userdataWindow.exec();
}

void MainWindow::on_freshButton_clicked()
{
    this->showQuestions();
}

void MainWindow::on_signoutButton_clicked()
{
    QMessageBox box (QMessageBox::NoIcon,tr("注销"),tr("确定注销?"),QMessageBox::Yes|QMessageBox::No,this);
    box.setIconPixmap(QPixmap(".//image/signout.png"));
    QIcon icon(".//image/out.ico");
    box.setWindowIcon(icon);
    box.setButtonText(QMessageBox::Yes,QString("确定"));
    box.setButtonText(QMessageBox::No,QString("取消"));
    if(box.exec()==QMessageBox::Yes)
    {
        this->hide();
        SignIn signin;
        signin.setAutoFillBackground(true);
        QPalette p_signin;
        QPixmap pixmap_signin(".//image/594_492.png");
        p_signin.setBrush(QPalette::Window, QBrush(pixmap_signin));
        signin.setPalette(p_signin);
        signin.show();

        if(signin.exec()==QDialog::Accepted)
          this->show();
        else
          this->close();
    }
}

void MainWindow::on_focusButton_clicked()
{
     FocusWindow* fw = new FocusWindow;//这里坑!!
     qDebug()<<"0";

     fw->setAutoFillBackground(true);
     QPalette pallete;
     QPixmap pixmap(".//image/bg7.jpg");
     pallete.setBrush(QPalette::Window, QBrush(pixmap));
     fw->setPalette( pallete);qDebug()<<"21";
     fw->show();qDebug()<<"22";
     fw->showTable(1);qDebug()<<"23";
     qDebug()<<"20";
}

void MainWindow::on_followedButton_clicked()
{
    FocusWindow* fw = new FocusWindow;//这里坑!!
    qDebug()<<"0";

    fw->setAutoFillBackground(true);
    QPalette pallete;
    QPixmap pixmap(".//image/bg7.jpg");
    pallete.setBrush(QPalette::Window, QBrush(pixmap));
    fw->setPalette( pallete);qDebug()<<"21";
    fw->show();qDebug()<<"22";
    fw->showTable(0);qDebug()<<"23";
    qDebug()<<"20";
}

void MainWindow::on_homepageButton_clicked()
{
    qrit = Questions.rbegin();

    this->on_nextpageButton_clicked();
    page = 1;
    ui->pageNum->setText(QString::number(page));
    qDebug()<<"homepage";
}

void MainWindow::on_lastpageButton_clicked()
{
    if (qrit!=Questions.rend())
        qrit-=10;
    else
    {
        int n = Questions.size()%10;
        qrit-=10+n;
    }

    this->on_nextpageButton_clicked();
    if(page>1)
        page--;
    ui->pageNum->setText(QString::number(page));
    qDebug()<<"lastpage";
}

void MainWindow::on_nextpageButton_clicked()
{
    int row=0;
    while(qrit!=Questions.rend()&&row<10)
    {
        Question ques = *qrit;
        ui->tableWidget->setRowCount(row+1);
        ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(ques.getId())));
        ui->tableWidget->setItem(row,1,new QTableWidgetItem(ques.getTitle()));
        ui->tableWidget->setItem(row,2,new QTableWidgetItem(Global::getUser(ques.getUserId()).getName()));
        ui->tableWidget->setItem(row,3,new QTableWidgetItem(QString::number(ques.getAnswerList().size())));
        ui->tableWidget->setItem(row,4,new QTableWidgetItem(ques.getTime()));
        for(int col = 0;col<5;col++)
            ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
        //qDebug()<<QString::number(ques.getId())<<" "<" "<" "<tableWidget->show();
    if(qrit!=Questions.rend())
    {
        page++;
        ui->pageNum->setText(QString::number(page));
        qDebug()<<"nextpage";
    }
}

void MainWindow::on_endpageButton_clicked()
{
    int p = Questions.size()/10;
    qrit = Questions.rbegin();
    qrit+=10*p;
    this->on_nextpageButton_clicked();
    page = p+1;
    ui->pageNum->setText(QString::number(page));
    qDebug()<<"endpage";

}

void MainWindow::on_gotopageButton_clicked()
{
    bool* ok = NULL;
    QString pst = ui->pageNum->text();
    int p = pst.toInt(ok,10);
    qrit = Questions.rbegin();
    qrit+=10*(p-1);
    this->on_nextpageButton_clicked();
    page = p;
    ui->pageNum->setText(QString::number(page));

}



void MainWindow::on_noticeButton_clicked()
{
    NoticeWindow *nw = new NoticeWindow;
    nw->show();
}

(4)提问
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第4张图片
ask.h

#ifndef ASK_H
#define ASK_H

#include 

namespace Ui {
class Ask;
}

class Ask : public QDialog
{
    Q_OBJECT

public:
    explicit Ask(QWidget *parent = 0);
    ~Ask();

private slots:
    void on_buttonBox_accepted();

    void on_buttonBox_rejected();

private:
    Ui::Ask *ui;
};

#endif // ASK_H

ask.cpp

#include "ask.h"
#include "ui_ask.h"
#include "question.h"
#include "global.h"

#include 
Ask::Ask(QWidget *parent) :
    QDialog(parent),
    ui(new Ui::Ask)
{
    ui->setupUi(this);
}

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

void Ask::on_buttonBox_accepted()
{
    Question ques;

    int id=Questions.size()+1;
    int userId=USER.getId();

    QString currentTitle = ui->lineEdit->text();
    QString currentContent = ui->textEdit->toPlainText();
    if(currentTitle!=""&¤tContent!="")
    {
        //ques.setContent(currentContent);
        QDateTime time = QDateTime::currentDateTime();//获取系统现在的时间
        QString timestr = time.toString("yyyy-MM-dd hh:mm:ss ddd"); //设置显示格式
        //ques.setTime(timestr);


        ques.created(id,userId,currentContent,timestr);
        ques.setTitle(currentTitle);

        USER.handleAskList(ques.getId(),1);
        Global::update(USER);
        Global::insert(ques);

        qDebug()<<"ask success";
    }
    else
    {
        QMessageBox fail(QMessageBox::NoIcon, "失败", "请输入完整的标题和内容");
        fail.addButton("确定", QMessageBox::AcceptRole);
        fail.exec();
    }
}

void Ask::on_buttonBox_rejected()
{
    this->close();
}

(5)问题与答案窗口
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第5张图片

quesanswindow.h

#ifndef QUESANSWINDOW_H
#define QUESANSWINDOW_H

#include 
#include "question.h"
#include "user.h"
#include "answer.h"
#include 
namespace Ui {
class QuesAnsWindow;
}

class QuesAnsWindow : public QWidget
{
    Q_OBJECT

public:
    explicit QuesAnsWindow(QWidget *parent = 0);
    ~QuesAnsWindow();

    void showQuesAnswers(int id);
    void freshTable();
    void setAsker(User user);
    void setQuestion(Question question);
    void setAnswers(vector answers);
    void setAnswerer(User user);
    void setCurAnswer(Answer ans);
    User getAnswerer();
    Answer getCurAnswer();
    vector getAnswers();
    User getAsker();
    Question getQuestion();

    void showAnswer(int id);

private slots:
    void on_answerQuesButton_clicked();

    void on_tableWidget_clicked(const QModelIndex &index);

    //void on_praiseButton_toggled(bool checked);

    //void on_focusTZButton_toggled(bool checked);

   // void on_focusDZButton_toggled(bool checked);

    void on_freshButton_clicked();

    //void on_praiseButton_clicked(bool checked);

    void on_praiseButton_clicked();

    void on_focusTZButton_clicked();

    void on_focusDZButton_clicked();

    void on_inviteButton_clicked();

    void on_aboutTZButton_clicked();

    void on_aboutDZButton_clicked();

    void on_commentButton_clicked();

private:
    Ui::QuesAnsWindow *ui;

    User asker;
    User answerer;
    Answer curAnswer;
    Question question;
    vector answers;
};

#endif // QUESANSWINDOW_H

quesanswindow.cpp

#include "quesanswindow.h"
#include "ui_quesanswindow.h"
#include "answer.h"
#include "global.h"
#include "invitedialog.h"
#include "userdatawindow.h"
#include "commentdialog.h"
#include 
#include 
QuesAnsWindow::QuesAnsWindow(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::QuesAnsWindow)
{
    ui->setupUi(this);
    this->setAutoFillBackground(true);
    QPalette palette;
    QPixmap pixmap(".//image/bg4.jpg");
    palette.setBrush(QPalette::Window, QBrush(pixmap));
    this->setPalette(palette);

    this->resize(800,764);
    this->setFixedSize(800,764);
    ui->tableWidget->setRowCount(0);
    ui->tableWidget->setColumnCount(5);
    ui->tableWidget->verticalHeader()->setDefaultSectionSize(50);
    ui->tableWidget->setFont(QFont("微软雅黑", 10, QFont::Bold ));
    ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);
    QStringList header;
    header<"被赞数")<"答主")<"答案ID")<"答主ID")<"时间");
    ui->tableWidget->setHorizontalHeaderLabels(header);
    ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
    ui->tableWidget->setShowGrid(false);
    ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
    ui->tableWidget->setStyleSheet("background-color:rgba(0,0,0,50)");
    ui->tableWidget->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->show();
    ui->textBrowser->setStyleSheet("background-color:rgba(0,0,0,50)");
    ui->textBrowser_2->setStyleSheet("background-color:rgba(0,0,0,50)");
    ui->textEdit->setStyleSheet("background-color:rgba(0,0,0,50)");

    ui->praiseButton->setVisible(false);
    ui->focusDZButton->setVisible(false);
    ui->commentButton->setVisible(false);
    ui->aboutDZButton->setVisible(false);
    ui->textBrowser->setFont(QFont("微软雅黑", 12, QFont::Light ));
    ui->textBrowser->setTextColor(QColor("white"));
    ui->textBrowser_2->setFont(QFont("微软雅黑", 12, QFont::Light ));
    ui->textBrowser_2->setTextColor(QColor("white"));
    ui->textEdit->setFont(QFont("微软雅黑", 12, QFont::Light ));
    ui->textEdit->setTextColor(QColor("white"));
}

QuesAnsWindow::~QuesAnsWindow()
{
    delete ui;
}
void QuesAnsWindow::setAsker(User user)
{
    this->asker = user;
}

void QuesAnsWindow::setQuestion(Question question)
{
    this->question = question;
}

User QuesAnsWindow::getAsker()
{
    return this->asker;
}

Question QuesAnsWindow::getQuestion()
{
    return this->question;
}
void QuesAnsWindow::setAnswers(vector answers)
{
    this->answers = answers;
}

vector QuesAnsWindow::getAnswers()
{
    return this->answers;
}
void QuesAnsWindow::setAnswerer(User user)
{
    this->answerer = user;
}

void QuesAnsWindow::setCurAnswer(Answer ans)
{
    this->curAnswer = ans;
}

User QuesAnsWindow::getAnswerer()
{
    return this->answerer;
}

Answer QuesAnsWindow::getCurAnswer()
{
    return this->curAnswer;
}

void QuesAnsWindow::showQuesAnswers(int id)
{
    Question ques = Global::getQuestion(id);//问题
    this->setQuestion(ques);

    ui->label_title->setText(ques.getTitle());
    ui->textBrowser_2->setText(ques.getContent());
    ui->label_time->setText(ques.getTime());

    User user = Global::getUser(ques.getUserId());//题主
    this->setAsker(user);
    ui->label_tizhu->setText(user.getName());
    vector<int>ansIds = ques.getAnswerList();
    vectoranswers;
    //所有回答
    for(vector<int>::iterator it = ansIds.begin();it!=ansIds.end();++it)
    {
           Answer ans=Global::getAnswer((*it));
           answers.push_back(ans);

    }
    this->setAnswers(answers);//所有回答
    int flag=0;
    int row = 0;
    for(vector::reverse_iterator rit = answers.rbegin();rit!=answers.rend();++rit)
    {
        Answer ans = *rit;
        ui->tableWidget->setRowCount(row+1);
        ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(ans.getPraisedNum())));
        ui->tableWidget->setItem(row,1,new QTableWidgetItem(Global::getUser(ans.getUserId()).getName()));
        ui->tableWidget->setItem(row,2,new QTableWidgetItem(QString::number(ans.getId())));
        ui->tableWidget->setItem(row,3,new QTableWidgetItem(QString::number(ans.getUserId())));
        ui->tableWidget->setItem(row,4,new QTableWidgetItem(ans.getTime()));

        qDebug()<" "<" "<" "<1;
    }
    for(int row = 0;row < answers.size();row++)
    {
        for(int col = 0;col<5;col++)
            ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
    }
    if(flag==0)
         ui->tableWidget->setRowCount(0);
    ui->tableWidget->show();
    //检查是否关注题主
    bool flag1 = true;
    User tmpU = this->getAsker();
    if (tmpU.getId()!=USER.getId())
    {
        ui->focusTZButton->setCheckable(true);
        vector<int> focusls = USER.getFocusList();
        for(vector<int>::iterator it = focusls.begin();it != focusls.end();++it)
        {
            User u = Global::getUser(*it);
            if(u.getId()==-1)
                break;
            if(tmpU.getId()== *it)
            {
                flag1=false;//已经关注了
                ui->focusTZButton->setChecked(true);

                ui->focusTZButton->setText("取消关注");
                qDebug()<<"取消关注";
                break;

            }
        }
        if(flag1)
       {
            ui->focusTZButton->setChecked(false);
            ui->focusTZButton->setText("关注题主");
        }
    }
    else
    {
        ui->focusTZButton->setVisible(false);
        ui->aboutTZButton->setVisible(false);
    }
}
void QuesAnsWindow::freshTable()
{

    vectoranswers = this->getAnswers();
    qDebug()<<"freshTable"<<this->getAnswers().size();
    int flag=0;
    int row = 0;
    for(vector::reverse_iterator rit = answers.rbegin();rit!=answers.rend();++rit)
    {
        Answer ans = *rit;

        ui->tableWidget->setRowCount(row+1);
        ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(ans.getPraisedNum())));
        ui->tableWidget->setItem(row,1,new QTableWidgetItem(Global::getUser(ans.getUserId()).getName()));
        ui->tableWidget->setItem(row,2,new QTableWidgetItem(QString::number(ans.getId())));
        ui->tableWidget->setItem(row,3,new QTableWidgetItem(QString::number(ans.getUserId())));
        ui->tableWidget->setItem(row,4,new QTableWidgetItem(ans.getTime()));


        qDebug()<" "<" "<" "<1;
    }
    for(int row = 0;row < answers.size();row++)
    {
        for(int col = 0;col<5;col++)
            ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
    }
    if(flag==0)
         ui->tableWidget->setRowCount(0);
    ui->tableWidget->show();

}

void QuesAnsWindow::on_answerQuesButton_clicked()
{
    qDebug()<<"6begin";
    QString currentContent = ui->textEdit->document()->toPlainText();
    if(currentContent!="")
    {
        Answer answer;
        int id=Answers.size()+1;

        //answer.setContent(currentContent);
        int userId=USER.getId();
        QDateTime time = QDateTime::currentDateTime();//获取系统现在的时间
        QString timestr = time.toString("yyyy-MM-dd hh:mm:ss ddd"); //设置显示格式
        //answer.setTime(timestr);
        answer.created(id,userId,currentContent,timestr);
        answer.setPraisedNum(0);
        answer.setQuestionId(this->getQuestion().getId());
        qDebug()<<"5";

        vector<int> answerlist = this->getQuestion().getAnswerList();
        answerlist.push_back(answer.getId());

        qDebug()<<"4";

        //this->setQuestion(this->getQuestion().setAnswerList(answerlist));//大坑啊,这个一定要总结错误
        Question tmpQ = this->getQuestion();
        tmpQ.setAnswerList(answerlist);
        this->setQuestion(tmpQ);
        qDebug()<<"3";

        vector answers = this->getAnswers();
        answers.push_back(answer);
        qDebug()<<"answer"<<this->getAnswers().size();
        this->setAnswers(answers);
        qDebug()<<"answer"<<this->getAnswers().size();

        USER.handleAnswerList(answer.getId(),1);
        qDebug()<<"2";
        try
        {
            std::cout<catch(...)
        {
            qDebug()<<"cout<;
            Global::insert(answer);
        }
        Global::update(this->getQuestion());
        Global::update(USER);
        this->freshTable();
        ui->textEdit->clear();
    }
    else
    {
        QMessageBox fail(QMessageBox::NoIcon, "失败", "请输入搜索内容");
        fail.addButton("确定", QMessageBox::AcceptRole);
        fail.exec();
    }
    qDebug()<<"1end";

}
void QuesAnsWindow::showAnswer(int id)
{
    Answer ans;
    ans = Global::getAnswer(id);

    User ansuser = Global::getUser(ans.getUserId());
    this->setAnswerer(ansuser);
    this->setCurAnswer(ans);
    qDebug()<<"on_tableWidget_clicked"<<this->getCurAnswer().getId()<<this->getCurAnswer().getContent();
    ui->label_dazhu->setText(ansuser.getName());
    ui->label_time->setText(ans.getTime());
    ui->label_prsnum->setText(QString::number(ans.getPraisedNum()));
    ui->textBrowser->setText(ans.getContent());

    if(ansuser.getId()==USER.getId())
    {
       ui->praiseButton->setVisible(false);
       ui->focusDZButton->setVisible(false);
       ui->aboutDZButton->setVisible(false);
       ui->commentButton->setVisible(false);

    }
    else
    {
       ui->praiseButton->setVisible(true);
       ui->focusDZButton->setVisible(true);
       ui->aboutDZButton->setVisible(true);
        ui->commentButton->setVisible(true);
       ui->praiseButton->setCheckable(true);
       ui->focusDZButton->setCheckable(true);

    }
    bool flag1 = true;
    vector<int> praisels = USER.getPraiseList();
    for(vector<int>::iterator it = praisels.begin();it != praisels.end();++it)
    {
        if(*it > Answers.size()||*it<0)
            break;
        Answer tmpA = Global::getAnswer(*it);

        if(tmpA.getId()== this->getCurAnswer().getId())
        {
            flag1=false;//已经赞过了
            ui->praiseButton->setChecked(true);
            ui->praiseButton->setText("取消赞");
            break;
        }

    }
    if(flag1)
    {
        ui->praiseButton->setChecked(false);
        ui->praiseButton->setText("赞");
    }
    //检查是否已经关注答主
    User tmpU = this->getAnswerer();
    bool flag2 = true;
    vector<int> focusls = USER.getFocusList();
    for(vector<int>::iterator it = focusls.begin();it != focusls.end();++it)
    {
        User u = Global::getUser(*it);
        if(u.getId()==-1)
            break;
        if(tmpU.getId()== *it)
        {
            flag2=false;//已经关注了
            ui->focusDZButton->setChecked(true);
            ui->focusDZButton->setText("取消关注");
            break;

        }
    }
    if(flag2)
    {
        ui->focusDZButton->setChecked(false);
        ui->focusDZButton->setText("关注答主");
    }
    //qDebug()<<"on_tableWidget_clicked";
}

void QuesAnsWindow::on_tableWidget_clicked(const QModelIndex &index)
{
    bool* ok = NULL;
    int id =ui->tableWidget->item(index.row(),2)->text().toInt(ok,10);
    qDebug()<<"on_tableWidget_clicked"<void QuesAnsWindow::on_freshButton_clicked()
{
    freshTable();
}

//关注某人创建通知
void focusNotice(User user)
{
    //创建通知
    Notification notif;
    int id = Notifications.size()+1;
    int userId =user.getId();
    int senderId = USER.getId();
    int questionId = 0;
    int answerId = 0;
    QDateTime time = QDateTime::currentDateTime();//获取系统现在的时间
    QString timestr = time.toString("yyyy-MM-dd hh:mm:ss ddd"); //设置显示格式
    QString title = QString("%1 关注了你").arg(USER.getName());
    QString content = "";
    notif.created(id,userId,content,timestr);
    notif.setQuestionId(questionId);
    notif.setAnswerId(answerId);
    notif.setSenderId(senderId);
    notif.setType(3);
    notif.setTitle(title);

    Global::insert(notif);
}


void QuesAnsWindow::on_praiseButton_clicked()
{
    qDebug()<<"begin";
    User tmpU = this->getAnswerer();
    qDebug()<<"on_praiseButton_clicked()"<<this->getCurAnswer().getId()<<this->getCurAnswer().getContent();
    if(tmpU.getId()!=USER.getId())
    {
        bool flag = true;
        vector<int> praisels = USER.getPraiseList();
        for(vector<int>::iterator it = praisels.begin();it != praisels.end();++it)
        {
            if(*it > Answers.size()|| *it<0)
                break;
            Answer tmpA = Global::getAnswer(*it);
            qDebug()<<"tmpA"<" "<"flag1"<<this->getCurAnswer().getId()<<this->getCurAnswer().getContent();
            if(tmpA.getId()== this->getCurAnswer().getId())
            {
                qDebug()<<"flag2";

                flag=false;//已经赞过了
                ui->praiseButton->setText("取消赞");
                qDebug()<<"flag3";
                break;

            }

            qDebug()<if(flag)
        {
            qDebug()<<"flag5";
            int upn= tmpU.getPraisedNum();
            //this->setAnswerer(this->getAnswerer().setPraisedNum(upn+1));


            tmpU.setPraisedNum(upn+1);
            this->setAnswerer(tmpU);
             qDebug()<<"flag4";
            Global::update(this->getAnswerer());

            int apn=this->getCurAnswer().getPraisedNum();
            //this->setCurAnswer(this->getCurAnswer().setPraisedNum(apn+1));
            qDebug()<<"flag3";
            Answer tmpA = this->getCurAnswer();
            tmpA.setPraisedNum(apn+1);
            this->setCurAnswer(tmpA);
            qDebug()<<"flag2";
            Global::update(this->getCurAnswer());
            ui->label_prsnum->setText(QString::number(apn+1));
            ui->praiseButton->setChecked(true);
            ui->praiseButton->setText("取消赞");
            qDebug()<<"flag1";

            USER.handlePraiseList(this->getCurAnswer().getId(),1);
            Global::update(USER);
            qDebug()<<"flag=true";
            //创建通知
            Notification notif;

            int id = Notifications.size()+1;
            int userId =this->getAnswerer().getId();
            int senderId = USER.getId();
            int questionId = this->getQuestion().getId();
            int answerId = this->getCurAnswer().getId();
            QDateTime time = QDateTime::currentDateTime();//获取系统现在的时间
            QString timestr = time.toString("yyyy-MM-dd hh:mm:ss ddd"); //设置显示格式
            QString title = QString("%1 赞了你的回答").arg(USER.getName());
            QString content = this->getCurAnswer().getContent();
            notif.created(id,userId,content,timestr);
            notif.setQuestionId(questionId);
            notif.setAnswerId(answerId);
            notif.setSenderId(senderId);
            notif.setType(2);
            notif.setTitle(title);

            Global::insert(notif);
        }
        else
        {   qDebug()<<"f4";
            int upn=tmpU.getPraisedNum();
            //this->setAnswerer(this->getAnswerer().setPraisedNum(upn+1));


            tmpU.setPraisedNum(upn-1);
            this->setAnswerer(tmpU);
            qDebug()<<"f3";
            Global::update(this->getAnswerer());
            int apn=(this->getCurAnswer()).getPraisedNum();
            //this->setCurAnswer(this->getCurAnswer().setPraisedNum(apn+1));
            qDebug()<<"f2";
            Answer tmpA = this->getCurAnswer();
            tmpA.setPraisedNum(apn-1);
            this->setCurAnswer(tmpA);
            qDebug()<<"f1";
            Global::update(this->getCurAnswer());
            ui->label_prsnum->setText(QString::number(apn-1));
            qDebug()<<"f0";
            ui->praiseButton->setChecked(false);
            ui->praiseButton->setText("赞");
            USER.handlePraiseList(this->getCurAnswer().getId(),0);qDebug()<<this->getCurAnswer().getId()<<" "<<this->getCurAnswer().getPraisedNum();
            Global::update(USER);qDebug()<"flag=false";
        }
    }
}

void QuesAnsWindow::on_focusTZButton_clicked()
{
    User tmpU = this->getAsker();
    if(tmpU.getId()!=USER.getId())
    {
        bool flag = true;
        vector<int> focusls=USER.getFocusList();//这又是一个大大的坑!!!!这是为什么呢????
        for(vector<int>::iterator it= focusls.begin(); it != focusls.end(); ++it)
        {
            User u = Global::getUser(*it);
             qDebug()<<"onfocusTZbt"<" "<" "<<*it;
            if(u.getId()==-1)
                break;
            if(tmpU.getId()== *it)
            {
                flag=false;//已经关注了

                break;
            }
        }
        if(flag)
        {

            tmpU.handleFollowedList(USER.getId(),1);
            this->setAsker(tmpU);

            USER.handleFocusList(this->getAsker().getId(),1);
            Global::update(this->getAsker());
            Global::update(USER);
            focusNotice(this->getAsker());
            ui->focusTZButton->setChecked(true);
            ui->focusTZButton->setText("取消关注");
            qDebug()<<"取消关注"<else
        {

            tmpU.handleFollowedList(USER.getId(),0);
            qDebug()<<"flag=false"<<this->getAsker().getId()<<" "<this->setAsker(tmpU);
            qDebug()<<"flag=false"<<this->getAsker().getId();
            //this->getAsker().handleFollowedList(USER.getId(),0);
            USER.handleFocusList(this->getAsker().getId(),0);
            qDebug()<<"USER.handleFocusList"<<this->getAsker().getId();
            Global::update(this->getAsker());
            Global::update(USER);
            ui->focusTZButton->setChecked(false);
            ui->focusTZButton->setText("关注题主");
            qDebug()<<"关注题主"<void QuesAnsWindow::on_focusDZButton_clicked()
{
    User tmpU = this->getAnswerer();
    if( tmpU.getId()!=USER.getId())
    {
        bool flag = true;
        vector<int> focusls = USER.getFocusList();
        for(vector<int>::iterator it = focusls.begin();it != focusls.end();++it)
        {
            User u = Global::getUser(*it);
            qDebug()<<"onfocusDZbt"<" "<" "<<*it;;
            if(u.getId()==-1)
                break;
            if(tmpU.getId()== *it)
            {
                flag=false;//已经关注了

                break;
            }
        }
        if(flag)
        {

            tmpU.handleFollowedList(USER.getId(),1);
            this->setAnswerer(tmpU);
            //this->getAnswerer().handleFollowedList(USER.getId(),1);

            USER.handleFocusList(this->getAnswerer().getId(),1);
            Global::update(this->getAnswerer());
            Global::update(USER);
            focusNotice(this->getAnswerer());
            ui->focusDZButton->setChecked(true);
            ui->focusDZButton->setText("取消关注");
            qDebug()<<"取消关注"<else
        {

            tmpU.handleFollowedList(USER.getId(),0);
            this->setAnswerer(tmpU);
            //this->getAnswerer().handleFollowedList(USER.getId(),0);
            USER.handleFocusList(this->getAnswerer().getId(),0);
            Global::update(this->getAnswerer());
            Global::update(USER);
            ui->focusDZButton->setChecked(false);
            ui->focusDZButton->setText("关注答主");
            qDebug()<<"关注答主"<void QuesAnsWindow::on_inviteButton_clicked()
{
    InviteDialog *ivtdlg = new InviteDialog;
    ivtdlg->setQuestionId(this->getQuestion().getId());
    ivtdlg->exec();
}


void QuesAnsWindow::on_aboutTZButton_clicked()
{
    UserdataWindow *uw = new UserdataWindow;
    uw->setUserId(this->getAsker().getId());
    uw->show();
    uw->showAllDatas();
    this->hide();
}

void QuesAnsWindow::on_aboutDZButton_clicked()
{
    UserdataWindow *uw = new UserdataWindow;
    uw->setUserId(this->getAnswerer().getId());
    uw->show();
    uw->showAllDatas();
    this->hide();
}

void QuesAnsWindow::on_commentButton_clicked()
{
    CommentDialog *cmtDlg = new CommentDialog; 
    cmtDlg->setAnswerId(this->getCurAnswer().getId());
    cmtDlg->setAnswererId(this->getAnswerer().getId());
    cmtDlg->showComments();
    cmtDlg->exec();

}

(6)个人中心页面
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第6张图片

userdatawindow.h

#ifndef USERDATAWINDOW_H
#define USERDATAWINDOW_H

#include "user.h"
#include 

namespace Ui {
class UserdataWindow;
}

class UserdataWindow : public QDialog
{
    Q_OBJECT

public:
    explicit UserdataWindow(QWidget *parent = 0);
    ~UserdataWindow();
    void showAllDatas();
    void showUserDatas();
    void showQuestions();
    void showAnswers();
    int getUserId();
    void setUserId(int id);

private slots:
    void on_changePassButton_clicked();

    void on_changeNameButton_clicked();


    void on_tableWidget_doubleClicked(const QModelIndex &index);

    void on_tableWidget_2_doubleClicked(const QModelIndex &index);


    void on_messageButton_clicked();

private:
    Ui::UserdataWindow *ui;
    int userId;
};

#endif // USERDATAWINDOW_H

userdatawindow.cpp

#ifndef USERDATAWINDOW_H
#define USERDATAWINDOW_H

#include "user.h"
#include 

namespace Ui {
class UserdataWindow;
}

class UserdataWindow : public QDialog
{
    Q_OBJECT

public:
    explicit UserdataWindow(QWidget *parent = 0);
    ~UserdataWindow();
    void showAllDatas();
    void showUserDatas();
    void showQuestions();
    void showAnswers();
    int getUserId();
    void setUserId(int id);

private slots:
    void on_changePassButton_clicked();

    void on_changeNameButton_clicked();


    void on_tableWidget_doubleClicked(const QModelIndex &index);

    void on_tableWidget_2_doubleClicked(const QModelIndex &index);


    void on_messageButton_clicked();

private:
    Ui::UserdataWindow *ui;
    int userId;
};

#endif // USERDATAWINDOW_H

(7)关注列表(粉丝列表)
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第7张图片

focuswindow.h

#ifndef FOCUSWINDOW_H
#define FOCUSWINDOW_H

#include 

namespace Ui {
class FocusWindow;
}

class FocusWindow : public QWidget
{
    Q_OBJECT

public:
    explicit FocusWindow(QWidget *parent = 0);
    void showTable(bool type);
    ~FocusWindow();


public slots:
    void onBtnClicked(void);

private slots:
    void on_tableWidget_doubleClicked(const QModelIndex &index);

private:
    Ui::FocusWindow *ui;
};

#endif // FOCUSWINDOW_H

focuswindow.cpp

#include "focuswindow.h"
#include "ui_focuswindow.h"
#include "global.h"
#include "userdatawindow.h"

#include 
FocusWindow::FocusWindow(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::FocusWindow)
{
    ui->setupUi(this);
    this->resize(1024,576);
    this->setFixedSize(1024,576);
    qDebug()<<"1";
    ui->tableWidget->setRowCount(0);
    ui->tableWidget->setColumnCount(8);
    ui->tableWidget->verticalHeader()->setDefaultSectionSize(50);
    ui->tableWidget->setFont(QFont("微软雅黑", 10, QFont::Bold ));
    ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);
    QStringList header;
    header<"ID")<"用户名")<"回答数")<"提问数")<"获赞数")<"关注数")<"粉丝数")<"操作");
    ui->tableWidget->setHorizontalHeaderLabels(header);
    ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
    ui->tableWidget->setShowGrid(false);
    ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
    ui->tableWidget->setStyleSheet("background-color:rgba(0,0,0,30)");
    ui->tableWidget->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->show();
    qDebug()<<"2";
    //vector<Question> questions = Db.queryAllQues();

}

FocusWindow::~FocusWindow()
{
    delete ui;
}
void FocusWindow::showTable(bool type)
{
    if(type)//查看我的关注
    {
        ui->label->setText("我的关注列表");
        int flag=0;
        int row = 0;
        qDebug()<<"24";
        for(int i = USER.getFocusList().size()-1;i>=0;i--)
        {
            int id = USER.getFocusList().at(i);
            User u = Global::getUser(id);
            if(u.getId()==-1)
                break;
            ui->tableWidget->setRowCount(row+1);
            ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(u.getId())));
            ui->tableWidget->setItem(row,1,new QTableWidgetItem(u.getName()));
            ui->tableWidget->setItem(row,2,new QTableWidgetItem(QString::number(u.getAnswerList().size())));
            ui->tableWidget->setItem(row,3,new QTableWidgetItem(QString::number(u.getAskList().size())));
            ui->tableWidget->setItem(row,4,new QTableWidgetItem(QString::number(u.getPraisedNum())));
            ui->tableWidget->setItem(row,5,new QTableWidgetItem(QString::number(u.getFocusList().size())));
            ui->tableWidget->setItem(row,6,new QTableWidgetItem(QString::number(u.getFollowedList().size())));
            QPushButton * pBtn = new QPushButton();
            pBtn->setText("取消关注");
            pBtn->setStyleSheet("color:rgb(255,255,255)");
            connect(pBtn, SIGNAL(clicked()), this, SLOT(onBtnClicked()));
            ui->tableWidget->setCellWidget(row,7,pBtn);
            qDebug()<<QString::number(u.getId())<<" "<" "<" "<<USER.getFocusList().size();
            row++;
            flag=1;
        }
        for(int row = 0;row < USER.getFocusList().size();row++)
        {
            for(int col = 0;col<7;col++)
                ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
        }
        if(flag==0)
             ui->tableWidget->setRowCount(0);
        ui->tableWidget->show();
         qDebug()<<"3";
    }
    else
    {
        ui->label->setText("我的粉丝列表");
        int flag=0;
        int row = 0;
        qDebug()<<"24";
        for(int i = USER.getFollowedList().size()-1;i>=0;i--)
        {
            int id = USER.getFollowedList().at(i);
            User u = Global::getUser(id);
            if(u.getId()==-1)
                break;
            ui->tableWidget->setRowCount(row+1);
            ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(u.getId())));
            ui->tableWidget->setItem(row,1,new QTableWidgetItem(u.getName()));
            ui->tableWidget->setItem(row,2,new QTableWidgetItem(QString::number(u.getAnswerList().size())));
            ui->tableWidget->setItem(row,3,new QTableWidgetItem(QString::number(u.getAskList().size())));
            ui->tableWidget->setItem(row,4,new QTableWidgetItem(QString::number(u.getPraisedNum())));
            ui->tableWidget->setItem(row,5,new QTableWidgetItem(QString::number(u.getFocusList().size())));
            ui->tableWidget->setItem(row,6,new QTableWidgetItem(QString::number(u.getFollowedList().size())));

            qDebug()<<QString::number(u.getId())<<" "<" "<" "<<USER.getFocusList().size();
            row++;
            flag=1;
        }
        for(int row = 0;row < USER.getFollowedList().size();row++)
        {
            for(int col = 0;col<7;col++)
                ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
        }
        if(flag==0)
             ui->tableWidget->setRowCount(0);
        ui->tableWidget->show();
         qDebug()<<"3";
    }

}
void FocusWindow::onBtnClicked(void)
{
    QPushButton * senderObj=qobject_cast<QPushButton *>(sender());
    if(senderObj == 0)
    {
        return;
    }
    QModelIndex index =ui->tableWidget->indexAt(QPoint(senderObj->frameGeometry().x(),senderObj->frameGeometry().y()));
    int row=index.row();
    qDebug()<<"row:"<NULL;
    int id =ui->tableWidget->item(index.row(),0)->text().toInt(ok,10);
    User user = Global::getUser(id);
    USER.handleFocusList(id,0);
    user.handleFollowedList(USER.getId(),0);
    Global::update(USER);
    Global::update(user);
    qDebug()<<"取消关注成功";
    this->showTable(1);
}

void FocusWindow::on_tableWidget_doubleClicked(const QModelIndex &index)
{
    bool* ok = NULL;
    int id =ui->tableWidget->item(index.row(),0)->text().toInt(ok,10);

    UserdataWindow *uw = new UserdataWindow;
    uw->setUserId(id);
    uw->show();
    uw->showAllDatas();
    this->close();
}

(8)搜索结果
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第8张图片

searchresult.h

#ifndef SEARCHRESULT_H
#define SEARCHRESULT_H

#include 
#include "question.h"
#include "answer.h"
#include "user.h"
namespace Ui {
class SearchResult;
}

class SearchResult : public QDialog
{
    Q_OBJECT

public:
    explicit SearchResult(QWidget *parent = 0);
    ~SearchResult();
    bool search(QString str);
    bool search(Question q);
    bool search(Answer a);
    bool search(User u);
    bool search(QDate d);

private:
    Ui::SearchResult *ui;
};

#endif // SEARCHRESULT_H

searchresult.cpp

#include "searchresult.h"
#include "ui_searchresult.h"
#include "global.h"

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

    this->resize(1024,576);
    this->setFixedSize(1024,576);
    this->setAutoFillBackground(true);
    QPalette palette;
    QPixmap pixmap(".//image/bg7.jpg");
    palette.setBrush(QPalette::Window, QBrush(pixmap));
    this->setPalette(palette);

    qDebug()<<"1";
    ui->tableWidget->setRowCount(0);
    ui->tableWidget->setColumnCount(5);
    ui->tableWidget->verticalHeader()->setDefaultSectionSize(30);
    ui->tableWidget->setFont(QFont("微软雅黑", 10, QFont::Bold ));
    ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);
    QStringList header;
    header<"ID")<"问题")<"回答数")<"题主")<"时间");
    ui->tableWidget->setHorizontalHeaderLabels(header);
    ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
    ui->tableWidget->setShowGrid(false);
    ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
    ui->tableWidget->setStyleSheet("background-color:rgba(0,0,0,30)");
    ui->tableWidget->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");

    ui->tableWidget_2->setRowCount(0);
    ui->tableWidget_2->setColumnCount(6);
    ui->tableWidget_2->verticalHeader()->setDefaultSectionSize(30);
    ui->tableWidget_2->setFont(QFont("微软雅黑", 10, QFont::Bold ));
    ui->tableWidget_2->setEditTriggers(QAbstractItemView::NoEditTriggers);
    QStringList header2;
    header2<"ID")<"回答")<"问题")<"获赞数")<"答主")<"时间");;
    ui->tableWidget_2->setHorizontalHeaderLabels(header2);
    ui->tableWidget_2->setSelectionBehavior(QAbstractItemView::SelectRows);
    ui->tableWidget_2->setShowGrid(false);
    ui->tableWidget_2->horizontalHeader()->setStretchLastSection(true);
    ui->tableWidget_2->setStyleSheet("background-color:rgba(0,0,0,30)");
    ui->tableWidget_2->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget_2->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");

    ui->tableWidget_3->setRowCount(0);
    ui->tableWidget_3->setColumnCount(5);
    ui->tableWidget_3->verticalHeader()->setDefaultSectionSize(50);
    ui->tableWidget_3->setFont(QFont("微软雅黑", 10, QFont::Bold ));
    ui->tableWidget_3->setEditTriggers(QAbstractItemView::NoEditTriggers);
    QStringList header3;
    header3<"ID")<"用户名")<"回答数")<"提问数")<"获赞数");
    ui->tableWidget_3->setHorizontalHeaderLabels(header3);
    ui->tableWidget_3->setSelectionBehavior(QAbstractItemView::SelectRows);
    ui->tableWidget_3->setShowGrid(false);
    ui->tableWidget_3->horizontalHeader()->setStretchLastSection(true);
    ui->tableWidget_3->setStyleSheet("background-color:rgba(0,0,0,30)");
    ui->tableWidget_3->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget_3->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
}

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

bool SearchResult::search(QString str)
{
    Question q;
    q.setTitle(str);
    this->search(q);
    qDebug()<<"search question";
    Answer a;
    a.setContent(str);
    this->search(a);
    qDebug()<<"search answer";
    User u;
    u.setName(str);
    this->search(u);
    qDebug()<<"search user";

}

bool SearchResult::search(Question q)
{
    int row=0;
    for(vector<Question>::iterator it = Questions.begin(); it!=Questions.end(); ++it)
    {
        Question que=*it;
        if(que.getTitle().contains(q.getTitle()))
        {
            ui->tableWidget->setRowCount(row+1);
            ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(que.getId())));
            ui->tableWidget->setItem(row,1,new QTableWidgetItem(que.getTitle()));
            ui->tableWidget->setItem(row,2,new QTableWidgetItem(QString::number(que.getAnswerList().size())));
            ui->tableWidget->setItem(row,3,new QTableWidgetItem(Global::getUser(que.getUserId()).getName()));
            ui->tableWidget->setItem(row,4,new QTableWidgetItem(que.getTime()));
            for(int col = 0;coltableWidget->columnCount();col++)
                ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
            row++;

        }
    }
    if(row == 0)
        ui->tableWidget->setItem(0,0,new QTableWidgetItem(QString("未找到相关问题")));
}

bool SearchResult::search(Answer a)
{
    int row=0;
    for(vector<Answer>::iterator it = Answers.begin(); it!=Answers.end(); ++it)
    {
        Answer ans=*it;
        if(ans.getContent().contains(a.getContent()))
        {
            ui->tableWidget_2->setRowCount(row+1);
            ui->tableWidget_2->setItem(row,0,new QTableWidgetItem(QString::number(ans.getId())));
            ui->tableWidget_2->setItem(row,1,new QTableWidgetItem(ans.getContent()));
            ui->tableWidget_2->setItem(row,2,new QTableWidgetItem(Global::getQuestion(ans.getQuestionId()).getTitle()));
            ui->tableWidget_2->setItem(row,3,new QTableWidgetItem(QString::number(ans.getPraisedNum())));
            ui->tableWidget_2->setItem(row,4,new QTableWidgetItem(Global::getUser(ans.getUserId()).getName()));
            ui->tableWidget_2->setItem(row,5,new QTableWidgetItem(ans.getTime()));
            for(int col = 0;coltableWidget_2->columnCount();col++)
                ui->tableWidget_2->item(row,col)->setTextColor(QColor(220,220,220));
            row++;
        }
    }
    if(row == 0)
        ui->tableWidget_2->setItem(0,0,new QTableWidgetItem(QString("未找到相关回答")));
}

bool SearchResult::search(User u)
{
    int row=0;
    for(vector<User>::iterator it = Users.begin(); it!=Users.end(); ++it)
    {
        User user=*it;
        if(user.getName().contains(u.getName()))
        {
            ui->tableWidget_3->setRowCount(row+1);
            ui->tableWidget_3->setItem(row,0,new QTableWidgetItem(QString::number(user.getId())));
            ui->tableWidget_3->setItem(row,1,new QTableWidgetItem(user.getName()));
            ui->tableWidget_3->setItem(row,2,new QTableWidgetItem(user.getAnswerList().size()));
            ui->tableWidget_3->setItem(row,3,new QTableWidgetItem(user.getAskList().size()));
            ui->tableWidget_3->setItem(row,4,new QTableWidgetItem(user.getPraisedNum()));
            for(int col = 0;coltableWidget_3->columnCount();col++)
                ui->tableWidget_3->item(row,col)->setTextColor(QColor(220,220,220));
            row++;
        }
    }
    if(row == 0)
        ui->tableWidget_3->setItem(0,0,new QTableWidgetItem(QString("未找到相关用户")));
}

bool SearchResult::search(QDate d)
{
    qDebug()<<"search question by time";
    QString timestr = d.toString("yyyy-MM-dd");
    ui->tableWidget_3->setVisible(false);
    ui->label_3->setVisible(false);
    this->resize(720,612);
    int row1=0;
    for(vector<Question>::iterator it = Questions.begin(); it!=Questions.end(); ++it)
    {
        Question que=*it;
        if(que.getTime().contains(timestr))
        {
            ui->tableWidget->setRowCount(row1+1);
            ui->tableWidget->setItem(row1,0,new QTableWidgetItem(QString::number(que.getId())));
            ui->tableWidget->setItem(row1,1,new QTableWidgetItem(que.getTitle()));
            ui->tableWidget->setItem(row1,2,new QTableWidgetItem(QString::number(que.getAnswerList().size())));
            ui->tableWidget->setItem(row1,3,new QTableWidgetItem(Global::getUser(que.getUserId()).getName()));
            ui->tableWidget->setItem(row1,4,new QTableWidgetItem(que.getTime()));
            for(int col = 0;coltableWidget->columnCount();col++)
                ui->tableWidget->item(row1,col)->setTextColor(QColor(220,220,220));
            row1++;

        }
    }
    if(row1 == 0)
        ui->tableWidget->setItem(0,0,new QTableWidgetItem(QString("未找到相关问题")));
    qDebug()<<"search answer by time";
    int row=0;
    for(vector<Answer>::iterator it = Answers.begin(); it!=Answers.end(); ++it)
    {
        Answer ans=*it;
        if(ans.getTime().contains(timestr))
        {
            ui->tableWidget_2->setRowCount(row+1);
            ui->tableWidget_2->setItem(row,0,new QTableWidgetItem(QString::number(ans.getId())));
            ui->tableWidget_2->setItem(row,1,new QTableWidgetItem(ans.getContent()));
            ui->tableWidget_2->setItem(row,2,new QTableWidgetItem(Global::getQuestion(ans.getQuestionId()).getTitle()));
            ui->tableWidget_2->setItem(row,3,new QTableWidgetItem(QString::number(ans.getPraisedNum())));
            ui->tableWidget_2->setItem(row,4,new QTableWidgetItem(Global::getUser(ans.getUserId()).getName()));
            ui->tableWidget_2->setItem(row,5,new QTableWidgetItem(ans.getTime()));
            for(int col = 0;coltableWidget_2->columnCount();col++)
                ui->tableWidget_2->item(row,col)->setTextColor(QColor(220,220,220));
            row++;
        }
    }
    if(row == 0)
        ui->tableWidget_2->setItem(0,0,new QTableWidgetItem(QString("未找到相关回答")));
    qDebug()<<"end search by time";
}

(9)通知消息窗口
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第9张图片

noticewindow.h

#ifndef NOTICEWINDOW_H
#define NOTICEWINDOW_H

#include 
#include 
namespace Ui {
class NoticeWindow;
}

class NoticeWindow : public QWidget
{
    Q_OBJECT

public:
    explicit NoticeWindow(QWidget *parent = 0);
    ~NoticeWindow();
    void showNotice();

private slots:


    void on_noticeButton_toggled(bool checked);

    void on_praiseButton_toggled(bool checked);

    void on_focusButton_toggled(bool checked);

    void on_messageButton_toggled(bool checked);


    void on_tableWidget_doubleClicked(const QModelIndex &index);

private:
    Ui::NoticeWindow *ui;
};

#endif // NOTICEWINDOW_H

noticewindow.cpp

#include "noticewindow.h"
#include "ui_noticewindow.h"
#include "global.h"
#include "quesanswindow.h"
#include "replydialog.h"
#include "userdatawindow.h"
#include "commentdialog.h"
NoticeWindow::NoticeWindow(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::NoticeWindow)
{
    ui->setupUi(this);
    QPalette pallete;
    QPixmap pixmap(".//image/bg7.jpg");
    pallete.setBrush(QPalette::Window, QBrush(pixmap));
    this->setPalette( pallete);
    ui->noticeButton->setChecked(true);
    this->showNotice();
}

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

void NoticeWindow::on_noticeButton_toggled(bool checked)
{
    if(checked)
    {
        this->showNotice();
    }

}
void  NoticeWindow::showNotice()
{
    ui->focusButton->setChecked(false);
    ui->praiseButton->setChecked(false);
    ui->messageButton->setChecked(false);

    ui->tableWidget->setRowCount(0);
    ui->tableWidget->setColumnCount(4);
    ui->tableWidget->verticalHeader()->setDefaultSectionSize(40);
    ui->tableWidget->setFont(QFont("微软雅黑", 10, QFont::Bold ));

    ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);
    QStringList header;
    header<"ID")<"标题")<"时间")<"问题ID");
    ui->tableWidget->setHorizontalHeaderLabels(header);
    ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
    ui->tableWidget->setShowGrid(false);
    ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
    ui->tableWidget->setStyleSheet("background-color:rgba(0,0,0,30)");
    ui->tableWidget->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->setColumnWidth(1,400);
    int row=0;
    for (vector<Notification>::iterator it = Notifications.begin();it!=Notifications.end();++it)
    {
        Notification notif = *it;

        if(notif.getUserId()==USER.getId() && notif.getType()==Type::Notice)
        {
            ui->tableWidget->setRowCount(row+1);
            ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(notif.getId())));
            ui->tableWidget->setItem(row,1,new QTableWidgetItem(notif.getTitle()));
            ui->tableWidget->setItem(row,2,new QTableWidgetItem(notif.getTime()));
            ui->tableWidget->setItem(row,3,new QTableWidgetItem(QString::number(notif.getQuestionId())));
            for(int col = 0;coltableWidget->columnCount();col++)
                ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
            //qDebug()<<QString::number(ques.getId())<<" "<" "<" "<void NoticeWindow::on_praiseButton_toggled(bool checked)
{
    if(checked)
    {
        ui->focusButton->setChecked(false);
        ui->noticeButton->setChecked(false);
        ui->messageButton->setChecked(false);

        ui->tableWidget->setRowCount(0);
        ui->tableWidget->setColumnCount(4);
        ui->tableWidget->verticalHeader()->setDefaultSectionSize(40);
        ui->tableWidget->setFont(QFont("微软雅黑", 10, QFont::Bold ));

        ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);
        QStringList header;
        header<"ID")<"标题")<"回答")<"时间");
        ui->tableWidget->setHorizontalHeaderLabels(header);
        ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
        ui->tableWidget->setShowGrid(false);
        ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
        ui->tableWidget->setStyleSheet("background-color:rgba(0,0,0,30)");
        ui->tableWidget->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
        ui->tableWidget->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
        ui->tableWidget->setColumnWidth(1,400);
        int row=0;
        for (vector<Notification>::iterator it = Notifications.begin();it!=Notifications.end();++it)
        {
            Notification notif = *it;

            if(notif.getUserId()==USER.getId() && notif.getType()==Type::Praise)
            {
                ui->tableWidget->setRowCount(row+1);
                ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(notif.getId())));
                ui->tableWidget->setItem(row,1,new QTableWidgetItem(notif.getTitle()));
                ui->tableWidget->setItem(row,2,new QTableWidgetItem(notif.getContent()));
                ui->tableWidget->setItem(row,3,new QTableWidgetItem(notif.getTime()));

                for(int col = 0;coltableWidget->columnCount();col++)
                    ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
                //qDebug()<<QString::number(ques.getId())<<" "<" "<" "<void NoticeWindow::on_focusButton_toggled(bool checked)
{
    if(checked)
    {
        ui->noticeButton->setChecked(false);
        ui->praiseButton->setChecked(false);
        ui->messageButton->setChecked(false);

        ui->tableWidget->setRowCount(0);
        ui->tableWidget->setColumnCount(4);
        ui->tableWidget->verticalHeader()->setDefaultSectionSize(40);
        ui->tableWidget->setFont(QFont("微软雅黑", 10, QFont::Bold ));

        ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);
        QStringList header;
        header<"ID")<"标题")<"时间")<"对方ID");
        ui->tableWidget->setHorizontalHeaderLabels(header);
        ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
        ui->tableWidget->setShowGrid(false);
        ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
        ui->tableWidget->setStyleSheet("background-color:rgba(0,0,0,30)");
        ui->tableWidget->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
        ui->tableWidget->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
        ui->tableWidget->setColumnWidth(1,400);
        int row=0;
        for (vector<Notification>::iterator it = Notifications.begin();it!=Notifications.end();++it)
        {
            Notification notif = *it;

            if(notif.getUserId()==USER.getId() && notif.getType()==Type::Focused)
            {
                ui->tableWidget->setRowCount(row+1);
                ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(notif.getId())));
                ui->tableWidget->setItem(row,1,new QTableWidgetItem(notif.getTitle()));
                ui->tableWidget->setItem(row,2,new QTableWidgetItem(notif.getTime()));
                ui->tableWidget->setItem(row,3,new QTableWidgetItem(QString::number(notif.getSenderId())));
                //ui->tableWidget->setItem(row,3,new QTableWidgetItem(QString::number(notif.getQuestionId())));
                for(int col = 0;coltableWidget->columnCount();col++)
                    ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
                //qDebug()<<QString::number(ques.getId())<<" "<" "<" "<void NoticeWindow::on_messageButton_toggled(bool checked)
{
    if(checked)
    {
        ui->focusButton->setChecked(false);
        ui->praiseButton->setChecked(false);
        ui->noticeButton->setChecked(false);

        ui->tableWidget->setRowCount(0);
        ui->tableWidget->setColumnCount(3);
        ui->tableWidget->verticalHeader()->setDefaultSectionSize(40);
        ui->tableWidget->setFont(QFont("微软雅黑", 10, QFont::Bold ));

        ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);
        QStringList header;
        header<"ID")<"标题")<"时间");
        ui->tableWidget->setHorizontalHeaderLabels(header);
        ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
        ui->tableWidget->setShowGrid(false);
        ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
        ui->tableWidget->setStyleSheet("background-color:rgba(0,0,0,30)");
        ui->tableWidget->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
        ui->tableWidget->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
        ui->tableWidget->setColumnWidth(1,400);

        /*因为迭代器类型搞错了
         * error: conversion from 'std::vector<Notification>::iterator {aka __gnu_cxx::__normal_iterator<Notification*,
         * std::vector<Notification> >}' to non-scalar type 'std::vector >::iterator
         * {aka __gnu_cxx::__normal_iterator > >}' requested
        */
        int row=0;
        for (vector<Notification>::iterator it = Notifications.begin();it!=Notifications.end();++it)
        {
            Notification notif = *it;

            if(notif.getUserId()==USER.getId() && notif.getType()==Type::Message)
            {
                ui->tableWidget->setRowCount(row+1);
                ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(notif.getId())));
                ui->tableWidget->setItem(row,1,new QTableWidgetItem(notif.getTitle()));
                ui->tableWidget->setItem(row,2,new QTableWidgetItem(notif.getTime()));
               // ui->tableWidget->setItem(row,3,new QTableWidgetItem(QString::number(notif.getQuestionId())));
                for(int col = 0;coltableWidget->columnCount();col++)
                    ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
                //qDebug()<<QString::number(ques.getId())<<" "<" "<" "<void NoticeWindow::on_tableWidget_doubleClicked(const QModelIndex &index)
{
    if(ui->noticeButton->isChecked())
    {
        bool* ok = NULL;
        int id =ui->tableWidget->item(index.row(),0)->text().toInt(ok,10);
        int quesId =ui->tableWidget->item(index.row(),3)->text().toInt(ok,10);
        Notification notif = Global::getNotification(id);
        if(notif.getAnswerId()==0)
        {
            QuesAnsWindow *qaw = new QuesAnsWindow;
            qaw->show();
            qaw->showQuesAnswers(quesId);
        }
        else
        {
            CommentDialog *cmtDlg = new CommentDialog;
            this->hide();
            cmtDlg->setAnswerId(notif.getAnswerId());
            cmtDlg->setAnswererId(quesId);
            cmtDlg->showComments();
            cmtDlg->exec();
        }

    }
    else if(ui->praiseButton->isChecked())
    {
        bool* ok = NULL;
        int id =ui->tableWidget->item(index.row(),0)->text().toInt(ok,10);
        Notification notif = Global::getNotification(id);
        int quesId = notif.getQuestionId();
        int ansId = notif.getAnswerId();
        QuesAnsWindow *qaw = new QuesAnsWindow;
        qaw->show();
        qaw->showQuesAnswers(quesId);
        qaw->showAnswer(ansId);

    }
    else if(ui->focusButton->isChecked())
    {
        bool* ok = NULL;
        int senderId =ui->tableWidget->item(index.row(),3)->text().toInt(ok,10);
        UserdataWindow *uw = new UserdataWindow;
        uw->setUserId(senderId);
        uw->show();
        uw->showAllDatas();
        this->hide();
    }
    else
    {
        bool* ok = NULL;
        int id =ui->tableWidget->item(index.row(),0)->text().toInt(ok,10);
        Notification notif = Global::getNotification(id);
        ReplyDialog *rplDlg = new ReplyDialog;
        rplDlg->setNotif(notif);
        rplDlg->showMessage();
        rplDlg->exec();
    }
}

(10)评论窗口
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第10张图片

commentdialog.h

#ifndef COMMENTDIALOG_H
#define COMMENTDIALOG_H

#include 

namespace Ui {
class CommentDialog;
}

class CommentDialog : public QDialog
{
    Q_OBJECT

public:
    explicit CommentDialog(QWidget *parent = 0);
    ~CommentDialog();

    void showComments();

    void setAnswerId(int id);
    int getAnswerId();

    void setAnswererId(int id);
    int getAnswererId();

private slots:
    void on_buttonBox_accepted();

    void on_buttonBox_rejected();

private:
    Ui::CommentDialog *ui;

    int answerId;
    int answererId;

};

#endif // COMMENTDIALOG_H

commentdialog.cpp

#include "commentdialog.h"
#include "ui_commentdialog.h"
#include "global.h"

#include 
CommentDialog::CommentDialog(QWidget *parent) :
    QDialog(parent),
    ui(new Ui::CommentDialog)
{
    ui->setupUi(this);
    QPalette pallete;
    QPixmap pixmap(".//image/small.png");
    pallete.setBrush(QPalette::Window, QBrush(pixmap));
    this->setPalette( pallete);
}

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

void CommentDialog::showComments()
{
    ui->tableWidget->setRowCount(0);
    ui->tableWidget->setColumnCount(3);
    ui->tableWidget->verticalHeader()->setDefaultSectionSize(40);
    ui->tableWidget->setFont(QFont("微软雅黑", 10, QFont::Bold ));

    ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);
    QStringList header;
    header<"评论")<"用户")<"时间");
    ui->tableWidget->setHorizontalHeaderLabels(header);
    ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
    ui->tableWidget->setShowGrid(false);
    ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
    ui->tableWidget->setStyleSheet("background-color:rgba(0,0,0,30)");
    ui->tableWidget->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->setColumnWidth(0,400);
    int row=0;
    for (vector<Notification>::iterator it = Notifications.begin();it!=Notifications.end();++it)
    {
        Notification notif = *it;

        if(notif.getType()==Type::Notice && notif.getAnswerId() == this->getAnswerId())
        {
            ui->tableWidget->setRowCount(row+1);
            ui->tableWidget->setItem(row,0,new QTableWidgetItem(notif.getContent()));
            ui->tableWidget->setItem(row,1,new QTableWidgetItem(Global::getUser(notif.getSenderId()).getName()));
            ui->tableWidget->setItem(row,2,new QTableWidgetItem(notif.getTime()));

            for(int col = 0;coltableWidget->columnCount();col++)
                ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
            //qDebug()<<QString::number(ques.getId())<<" "<" "<" "<void CommentDialog::setAnswerId(int id)
{
    this->answerId = id;
}

int CommentDialog::getAnswerId()
{
    return this->answerId;
}
void CommentDialog::setAnswererId(int id)
{
    this->answererId = id;
}

int CommentDialog::getAnswererId()
{
    return this->answererId;
}
void CommentDialog::on_buttonBox_accepted()
{
    QString content = ui->textEdit->toPlainText();
    if(content!="")
    {
        Notification notif;

        int id = Notifications.size()+1;
        int userId = this->getAnswererId();
        int senderId = USER.getId();
        QDateTime time = QDateTime::currentDateTime();//获取系统现在的时间
        QString timestr = time.toString("yyyy-MM-dd hh:mm:ss ddd"); //设置显示格式
        QString title = QString("%1 评论了你的回答 ").arg(USER.getName());
        notif.created(id,userId,content,timestr);

        notif.setQuestionId(Global::getAnswer(this->getAnswerId()).getQuestionId());
        notif.setAnswerId(this->getAnswerId());
        notif.setSenderId(senderId);
        notif.setType(1);
        notif.setTitle(title);

        Global::insert(notif);
    }
    else
    {
        QMessageBox fail(QMessageBox::NoIcon, "失败", "请输入评论内容");
        fail.addButton("确定", QMessageBox::AcceptRole);
        fail.exec();
    }

}

void CommentDialog::on_buttonBox_rejected()
{
    this->close();
}

(11)邀请他人页面
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第11张图片

invitedialog.h

#ifndef INVITEDIALOG_H
#define INVITEDIALOG_H

#include 

namespace Ui {
class InviteDialog;
}

class InviteDialog : public QDialog
{
    Q_OBJECT

public:
    explicit InviteDialog(QWidget *parent = 0);
    ~InviteDialog();
    void showFocus();
    void showFollowed();
    void showAll();

    int getQuestionId();
    void setQuestionId(int id);
private slots:
    void on_tableWidget_doubleClicked(const QModelIndex &index);



    void on_radioButton_clicked();

    void on_radioButton_2_clicked();

    void on_radioButton_3_clicked();


private:
    Ui::InviteDialog *ui;
    int questionId;
};

#endif // INVITEDIALOG_H

invitedialog.cpp

#include "invitedialog.h"
#include "ui_invitedialog.h"
#include "global.h"

#include 

InviteDialog::InviteDialog(QWidget *parent) :
    QDialog(parent),
    ui(new Ui::InviteDialog)
{
    ui->setupUi(this);
    QPalette pallete;
    QPixmap pixmap(".//image/small.png");
    pallete.setBrush(QPalette::Window, QBrush(pixmap));
    this->setPalette( pallete);

    ui->tableWidget->setRowCount(0);
    ui->tableWidget->setColumnCount(4);
    ui->tableWidget->verticalHeader()->setDefaultSectionSize(40);
    ui->tableWidget->setFont(QFont("微软雅黑", 10, QFont::Bold ));

    ui->tableWidget->setEditTriggers(QAbstractItemView::NoEditTriggers);
    QStringList header;
    header<"ID")<"名称")<"回答数")<"获赞数");
    ui->tableWidget->setHorizontalHeaderLabels(header);
    ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
    ui->tableWidget->setShowGrid(false);
    ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
    ui->tableWidget->setStyleSheet("background-color:rgba(0,0,0,30)");
    ui->tableWidget->horizontalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");
    ui->tableWidget->verticalHeader()->setStyleSheet("QHeaderView::section{background:skyblue;}");

    this->showFocus();
}

InviteDialog::~InviteDialog()
{
    delete ui;
}
int InviteDialog::getQuestionId()
{
    return this->questionId;
}
void InviteDialog::setQuestionId(int id)
{
    this->questionId=id;
}

void InviteDialog::showFocus()
{
    std::vector<int> focuslist = USER.getFocusList();
    int row=0;
    for(std::vector<int>::iterator it = focuslist.begin();it!=focuslist.end();++it)
    {
        User user = Global::getUser(*it);
        ui->tableWidget->setRowCount(row+1);
        ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(user.getId())));
        ui->tableWidget->setItem(row,1,new QTableWidgetItem(user.getName()));
        ui->tableWidget->setItem(row,2,new QTableWidgetItem(user.getAnswerList().size()));
        ui->tableWidget->setItem(row,3,new QTableWidgetItem(user.getPraisedNum()));
        for(int col = 0;coltableWidget->columnCount();col++)
            ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
        row++;
    }

}

void InviteDialog::showFollowed()
{
    std::vector<int> followedlist = USER.getFollowedList();
    int row=0;
    for(std::vector<int>::iterator it = followedlist.begin();it!=followedlist.end();++it)
    {
        User user = Global::getUser(*it);
        ui->tableWidget->setRowCount(row+1);
        ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(user.getId())));
        ui->tableWidget->setItem(row,1,new QTableWidgetItem(user.getName()));
        ui->tableWidget->setItem(row,2,new QTableWidgetItem(user.getAnswerList().size()));
        ui->tableWidget->setItem(row,3,new QTableWidgetItem(user.getPraisedNum()));
        for(int col = 0;coltableWidget->columnCount();col++)
            ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
        row++;
    }
}

void InviteDialog::showAll()
{
    int row=0;
    for(std::vector::iterator it = Users.begin();it!=Users.end();++it)
    {
        User user = *it;

        if(USER.getId()!=user.getId())
        {
            ui->tableWidget->setRowCount(row+1);
            ui->tableWidget->setItem(row,0,new QTableWidgetItem(QString::number(user.getId())));
            ui->tableWidget->setItem(row,1,new QTableWidgetItem(user.getName()));
            ui->tableWidget->setItem(row,2,new QTableWidgetItem(user.getAnswerList().size()));
            ui->tableWidget->setItem(row,3,new QTableWidgetItem(user.getPraisedNum()));
            for(int col = 0;coltableWidget->columnCount();col++)
                ui->tableWidget->item(row,col)->setTextColor(QColor(220,220,220));
            row++;
        }
    }
}

void InviteDialog::on_tableWidget_doubleClicked(const QModelIndex &index)
{
    Notification notif;
    bool* ok = NULL;
    int id = Notifications.size()+1;
    int userId =ui->tableWidget->item(index.row(),0)->text().toInt(ok,10);
    int senderId = USER.getId();
    int questionId = this->getQuestionId();
    QDateTime time = QDateTime::currentDateTime();//获取系统现在的时间
    QString timestr = time.toString("yyyy-MM-dd hh:mm:ss ddd"); //设置显示格式
    QString title = QString("%1 邀请你回答问题").arg(USER.getName());
    QString content = Global::getQuestion(questionId).getTitle();
    notif.created(id,userId,content,timestr);
    notif.setQuestionId(questionId);
    notif.setAnswerId(0);
    notif.setSenderId(senderId);
    notif.setType(1);
    notif.setTitle(title);

    Global::insert(notif);

    QMessageBox fail(QMessageBox::NoIcon, "成功", "邀请已发送");
    fail.addButton("确定", QMessageBox::AcceptRole);
    fail.exec();
    this->close();
}


void InviteDialog::on_radioButton_clicked()
{
    this->showFocus();

}

void InviteDialog::on_radioButton_2_clicked()
{
    this->showFollowed();
}

void InviteDialog::on_radioButton_3_clicked()
{
    this->showAll();
}

(12)私信(查看别人资料是可以给人私信)

QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第12张图片
这个忘记加图片背景了。。。
messagedialog.h

#ifndef MESSAGEDIALOG_H
#define MESSAGEDIALOG_H

#include 

namespace Ui {
class MessageDialog;
}

class MessageDialog : public QDialog
{
    Q_OBJECT

public:
    explicit MessageDialog(QWidget *parent = 0);
    ~MessageDialog();

    int getReceiverId();
    void setReceiverId(int id);

private slots:
    void on_buttonBox_accepted();

    void on_buttonBox_rejected();

private:
    Ui::MessageDialog *ui;
    int receiverId;
};

#endif // MESSAGEDIALOG_H

messagedialog.cpp

#include "messagedialog.h"
#include "ui_messagedialog.h"
#include "global.h"
#include 

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

MessageDialog::~MessageDialog()
{
    delete ui;
}
int MessageDialog::getReceiverId()
{
    return this->receiverId;
}
void MessageDialog::setReceiverId(int id)
{
    this->receiverId=id;
}

void MessageDialog::on_buttonBox_accepted()
{
    QString content = ui->textEdit->toPlainText();
    if(content!="")
    {
        Notification notif;

        int id = Notifications.size()+1;
        int userId = this->getReceiverId();
        int senderId = USER.getId();
        QDateTime time = QDateTime::currentDateTime();//获取系统现在的时间
        QString timestr = time.toString("yyyy-MM-dd hh:mm:ss ddd"); //设置显示格式
        QString title = QString("%1 给你发了一条私信").arg(USER.getName());
        notif.created(id,userId,content,timestr);
        notif.setQuestionId(0);
        notif.setAnswerId(0);
        notif.setSenderId(senderId);
        notif.setType(4);
        notif.setTitle(title);

        Global::insert(notif);
    }
    else
    {
        QMessageBox fail(QMessageBox::NoIcon, "失败", "请输入内容");
        fail.addButton("确定", QMessageBox::AcceptRole);
        fail.exec();
    }

}

void MessageDialog::on_buttonBox_rejected()
{
    this->close();
}

(13)回复窗口
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第13张图片
replydialog.h

#ifndef REPLYDIALOG_H
#define REPLYDIALOG_H
#include "notification.h"
#include 

namespace Ui {
class ReplyDialog;
}

class ReplyDialog : public QDialog
{
    Q_OBJECT

public:
    explicit ReplyDialog(QWidget *parent = 0);
    ~ReplyDialog();

    void setNotif(Notification notif);
    Notification getNotif();
    void showMessage();

private slots:
    void on_buttonBox_accepted();

private:
    Ui::ReplyDialog *ui;
    Notification notif;
};

#endif // REPLYDIALOG_H

replydialog.cpp

#include "replydialog.h"
#include "ui_replydialog.h"
#include "global.h"

#include 
ReplyDialog::ReplyDialog(QWidget *parent) :
    QDialog(parent),
    ui(new Ui::ReplyDialog)
{
    ui->setupUi(this);
    QPalette pallete;
    QPixmap pixmap(".//image/small.png");
    pallete.setBrush(QPalette::Window, QBrush(pixmap));
    this->setPalette( pallete);
}

ReplyDialog::~ReplyDialog()
{
    delete ui;
}
void ReplyDialog::setNotif(Notification notif)
{
    this->notif=notif;
}

Notification ReplyDialog::getNotif()
{
    return this->notif;
}
void ReplyDialog::showMessage()
{//原本把这部分放在构造函数里了,但是老师出错,原因是这里面用到了成员变量,而构造时还没有赋值,所以一直是金疙瘩,应该赋值notif后在show
    ui->textBrowser->setText(this->notif.getContent());
    ui->label->setText(Global::getUser(this->notif.getSenderId()).getName());
    ui->label_2->setText(USER.getName());
}

void ReplyDialog::on_buttonBox_accepted()
{
    QString content = ui->textEdit->toPlainText();
    if(content != "")
    {
        Notification notif;

        int id = Notifications.size()+1;
        int userId = this->notif.getSenderId();
        int senderId = USER.getId();
        QDateTime time = QDateTime::currentDateTime();//获取系统现在的时间
        QString timestr = time.toString("yyyy-MM-dd hh:mm:ss ddd"); //设置显示格式
        QString title = QString("%1 给你发了一条私信").arg(USER.getName());
        notif.created(id,userId,content,timestr);
        notif.setQuestionId(0);
        notif.setAnswerId(0);
        notif.setSenderId(senderId);
        notif.setType(4);
        notif.setTitle(title);

        Global::insert(notif);
    }
    else
    {
        QMessageBox fail(QMessageBox::NoIcon, "失败", "请输入内容");
        fail.addButton("确定", QMessageBox::AcceptRole);
        fail.exec();
    }
}

(14)修改密码
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第14张图片
changeprofile.h(名字取错了,但是改起来挺麻烦就没改了)

#ifndef CHANGEPROFILE_H
#define CHANGEPROFILE_H

#include 

namespace Ui {
class ChangeProfile;
}

class ChangeProfile : public QDialog
{
    Q_OBJECT

public:
    explicit ChangeProfile(QWidget *parent = 0);
    ~ChangeProfile();

private slots:
    void on_buttonBox_accepted();

    void on_buttonBox_rejected();

private:
    Ui::ChangeProfile *ui;
};

#endif // CHANGEPROFILE_H

changeprofile.cpp

#include "changeprofile.h"
#include "ui_changeprofile.h"
#include "global.h"

#include 
ChangeProfile::ChangeProfile(QWidget *parent) :
    QDialog(parent),
    ui(new Ui::ChangeProfile)
{
    ui->setupUi(this);
    ui->lineEdit_2->setEchoMode(QLineEdit::Password);
    ui->lineEdit_3->setEchoMode(QLineEdit::Password);

    QPalette pallete;
    QPixmap pixmap(".//image/small.png");
    pallete.setBrush(QPalette::Window, QBrush(pixmap));
    this->setPalette( pallete);
}

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

void ChangeProfile::on_buttonBox_accepted()
{
    QString oldPass = ui->lineEdit->text();
    if(oldPass != USER.getPassword())
    {
        QMessageBox fail(QMessageBox::NoIcon, "失败", "原密码错误");
        fail.addButton("确定", QMessageBox::AcceptRole);
        fail.exec();
    }
    else
    {
        QString newPass = ui->lineEdit_2->text();
        QString newPassCf = ui->lineEdit_3->text();
        if (newPass != newPassCf)
        {
            QMessageBox fail(QMessageBox::NoIcon, "失败", "两次密码不一致");
            ui->lineEdit_2->clear();
            ui->lineEdit_3->clear();
            fail.addButton("确定", QMessageBox::AcceptRole);
            fail.exec();
        }
        else
        {
            USER.setPassword(newPass);
            Global::update(USER);
        }
    }
}

void ChangeProfile::on_buttonBox_rejected()
{
    this->close();
}

(15)修改用户名
QT实现一个 “扯淡Universe” 单机问答系统,构建一个允许用户分享知识的平台_第15张图片
图中原用户名没有显示。。下面的代码中以及改了。

changename.h

#ifndef CHANGENAME_H
#define CHANGENAME_H

#include 

namespace Ui {
class ChangeName;
}

class ChangeName : public QDialog
{
    Q_OBJECT

public:
    explicit ChangeName(QWidget *parent = 0);
    ~ChangeName();

private slots:
    void on_buttonBox_accepted();

    void on_buttonBox_rejected();

private:
    Ui::ChangeName *ui;
};

#endif // CHANGENAME_H

changename.cpp

#include "changename.h"
#include "ui_changename.h"
#include "global.h"
ChangeName::ChangeName(QWidget *parent) :
    QDialog(parent),
    ui(new Ui::ChangeName)
{
    ui->setupUi(this);
    ui->label->setText(USER.getName());
    QPalette pallete;
    QPixmap pixmap(".//image/small.png");
    pallete.setBrush(QPalette::Window, QBrush(pixmap));
    this->setPalette( pallete);
}

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

void ChangeName::on_buttonBox_accepted()
{
    QString newName = ui->lineEdit->text();
    USER.setName(newName);
    Global::update(USER);
}

void ChangeName::on_buttonBox_rejected()
{
    this->close();
}

至此源代码都已经贴出,UI方面就只能靠自己看图咯,或者下载完整源码。

完成这个项目中遇到的教训
1. “基础设施”在前期要打好,后期就会事半功倍。这个基础设计并不仅仅指的是编程基础理论基础,比如我对于数据库操作的了解较少就遇到了很多新手常犯的错误,而且这个基础还指的是整个系统初期所做的一些事,比如类的成员有哪些,成员函数,还有一些常用的函数,比如按ID查询用户、问题答案这种前期就要写完善,否则到了后期如果还有错很难找到。成员变量没增加一个就得修改数据库中的一部分代码,没修改一次就增加了出错的几率。因此一开始尽量要想完善自己要做成什么样子,这个格局一开始就要打好,会在之后的工作中很方便。比如我一开始就想到自己需要加“粉丝”这个变量,因此在定义“focuslist”的时候就一起定义了“followedlist”。但是由于一开始没有想太远对于问题和回答对象的保存,所以之后才加的“answerlist”和“asklist”。
2. 由于将操作符重载定义写在了.h文件中,导致报了multiple definition的错误。应该讲重载的定义写在.cpp的,然后在类的定义中将操作符重载声明为友元。或者还能够通过在.h中在声明直接加上incline关键字。
3. 定义全局变量的过程也是充满曲折。一开始我只是新建了一个global.h文件,没有新建global.cpp,使用了extern关键字声明变量也没有用,后来又新建了一个Global类,里面放入全局变量,每个变量都是static的,但是还是编译报错。后来通过问同学才知道还得新建一个global.cpp,在里面再定义每个全局变量,只是不需要再加extern了。我两种全局变量的方法都用了,全局函数定义在Global类里,像所有问题,答案这种容器定义了extern。为了保持封装性,网上推荐使用使用Global类这种方式,使用extern则破坏了程序的封装性。
4. 新定义的窗口总是闪退。通过网上查询得知是因为我将窗口对象定义在栈中,每次都被释放了,而为了保持窗口应该定义在堆中。比如”Dialog dlg”应改成 “Dialog *dlg = new Dialog” 。
5. TableWidget的列数和我自己实现的数量不一样导致打卡那个窗口总是程序异常终止。TableWidget的使用需要十分小心,因为有多处使用,所以我在复制代码之后总是忘记“因地制宜”,没有修改行数导致运行不了。
6. 迭代器类型使用错误。因为我在类里定义的容器都是存的int类型的id,但是我将所有问题,答案等都是放在各地对应的容器,比如所有通知对象放在”vectorNotifications”中。导致我有次弄混,导致报了一个错:
“error: conversion from 'std::vector::iterator {aka __gnu_cxx::__normal_iterator >}' to non-scalar type 'std::vector >::iterator
7. 说到迭代器还有一个错误特别难找,在遍历用户的关注列表时我开始使用的下面这个循环
for(vector::iterator it= USER.getFocusList().begin(); it != USER.getFocusList().end(); ++it)”,但是总是输出一些奇怪的数字,我开始以为只是越界了,以为这个focuslist的end不对劲,所以开始我在网上查找解决方案的时候搜的是解决容器迭代器的越界问题,于是找到了使用at的方法,也就是相当于使用下标的方式,用一个i从0到USER.getFocusList().size(),然后提取USER.getFocusList().at(i)。问题是没有了,但是原因不是这个,原因是因为USER.getFocusList()是得到focuslist的一个副本,并不是得到focuslist本身,里面的值是一样但是保存的地址不同,每次使用USER.getFocusList()得到的也不是同一个变量,因此在USER.getFocusList().begin()USER.getFocusList().end()之间可能还有很多位置的东西,因为是一个容器的开头,另一个容器的结尾,自然这样遍历下去会输出一些异常的数字。所有我在for循环开始之前先定义一个临时容器保存USER.getFocusList(),然后for循环遍历这个临时容器,这样就解决了这个问题。
8. 关于get和set函数我还犯了一个类似的错误,原因还是忘记get函数得到的只是一个分身,所有只是改变分身对真身不会有任何影响。
9. 没有给成员变量赋值就调用了需要操作成员变量的成员函数。我希望在一个窗口打开的时候就展示数据,所以在构造函数中就写了展示函数show(),但是当我运行打开窗口的时候发现数据总是同一个人的,反正不是我所需要的那个人。后来发现是因为我是在构造函数执行了之后才赋值成员变量,所有展示出来的数据也不是我想要的数据了。因此在构造函数中我们应该尽量避免执行一些需要操作成员变量的函数,因为构造函数总是在声明的时候就执行了,而这个时候成员变量不一定赋值了。
10. 由于纯虚函数没有在子类中实现导致vtable reference,这个错误是很经典的,有时候忘记实现了就会编译错误,因为错了一两次后就基本不会犯了。
11. 关于数据库的方面的错误犯了很多。首先就是误用了sql里面的关键字,比如password就是一个,time也是,使用了这些关键字肯定会报错。然后就是parameter count mismatch,原因是因为我在声明数据库的时候多了或者少了一个逗号,又或者是在插入或更新是sql语句中多了个问号。关于数据库的知识还是得先多学习一下再上手可以少走很多弯路,节约一些时间,光是数据库的错误就占了我前期找错的一半的时间。

你可能感兴趣的:(qt,c++,问答系统,c++,qt)