首页 > 代码库 > 查询单词,综合例子。

查询单词,综合例子。

12.32 重写TextQuery和QueryResult类,用StrBlob代替vector<string>保存输入文件。

TextQuery.h

#ifndef TEXTQUERY_H#define TEXTQUERY_H#include<iostream>#include<string>#include<fstream>#include<vector>#include<memory>#include<map>#include<set>#include<new>#include"StrBlob.h"using namespace std;class QueryResult;class TextQuery{public:    using line_no=vector<string>::size_type;    TextQuery(StrBlob&);    QueryResult query(const string&) const;private:    shared_ptr<vector<string>> file;    map<string,shared_ptr<set<line_no>>> wm;};#endif // TEXTQUERY_H

TextQuery.cpp

#include"TextQuery.h"#include"QueryResult.h"#include<sstream>TextQuery::TextQuery(StrBlob& is):file(is.data){    string text;    auto vec=(is.data)->begin();    int n=0;    while(vec!=(is.data)->end())    {         text=*vec++;        //file->push_back(text);        string word;        istringstream line(text);        while(line>>word)        {            auto &lines=wm[word];            if(!lines)                lines.reset(new set<line_no>);            lines->insert(n);        }        ++n;    }}QueryResult TextQuery::query(const string& sought) const{    static shared_ptr<set<line_no>> nodata(new set<line_no>);    auto loc=wm.find(sought);    if(loc!=wm.end())        return QueryResult(sought,loc->second,file);    else        return QueryResult(sought,nodata,file);}

QueryResult.h

#ifndef QUERYRESULT_H#define QUERYRESULT_H#include <iostream>#include<memory>#include<vector>#include<string>#include<set>#include"TextQuery.h"using namespace std;class QueryResult{friend ostream& print(ostream& ,const QueryResult&);public:    QueryResult(string s,shared_ptr<set<TextQuery::line_no>> p,shared_ptr<vector<string>> f):sought(s),lines(p),file(f){}private:    string sought;    shared_ptr<set<TextQuery::line_no>> lines;    shared_ptr<vector<string>> file;};ostream& print(ostream& ,const QueryResult&);#endif

QueryResult.cpp

#include"QueryResult.h"ostream &print(ostream &os,const QueryResult &qr){    os<<qr.sought<<" occurs "<<qr.lines->size()<<" times "<<endl;    for(auto num:*qr.lines)        os<<"\t(line "<<num+1<<" ) "        <<(*qr.file)[num]<<endl;    return os;}

StrBlob.h

#ifndef STRBLOB_H#define STRBLOB_H#include<iostream>#include<string>#include<vector>#include<memory>using namespace std;class StrBlobPtr;class StrBlob{friend class StrBlobPtr;friend class TextQuery;public:    typedef string::size_type size_type;    //构造函数    StrBlob();    explicit StrBlob(initializer_list<string> il);    size_type size() const { return data->size(); }    bool empty() const { return data->empty();}    void push_back(const string &t) { data->push_back(t);}    void pop_back();    string& front();    string& back();    string& front() const;    string& back() const;    size_type count()    {        return data.use_count();    }    StrBlobPtr begin();    StrBlobPtr end();private:    shared_ptr<vector<string>> data;    void check(size_type i,const string msg) const;};#endif // STRBLOB_H

StrBlob.cpp

#include"StrBlob.h"#include"StrBlobPtr.h"StrBlob::StrBlob():data(new vector<string>){}StrBlob::StrBlob(initializer_list<string> il):data(make_shared<vector<string>>(il)){}void StrBlob::pop_back(){    check(0,"pop_back");    data->pop_back();}string& StrBlob::back(){    check(0,"back");    return data->back();}string& StrBlob::front(){    check(0,"front");    return data->front();}string& StrBlob::back() const{    check(0,"back");    return data->back();}string& StrBlob::front() const{    check(0,"front");    return data->front();}void StrBlob::check(size_type i, const string msg) const{    if(i>=data->size())        throw out_of_range(msg);}StrBlobPtr StrBlob::begin(){    return StrBlobPtr(*this);}StrBlobPtr StrBlob::end(){    return StrBlobPtr(*this,data->size());}

StrBlobPtr.h

#ifndef STRBLOBPTR_H#define STRBLOBPTR_H#include<string>#include<vector>#include<memory>using namespace std;class StrBlobPtr{public:    StrBlobPtr():curr(0) {}    StrBlobPtr(const StrBlob &a,size_t sz=0):wptr(a.data),curr(sz) {}    string& deref() const;    StrBlobPtr& incr();private:    shared_ptr<vector<string>> check(size_t,const string &) const;    weak_ptr<vector<string>> wptr;    size_t curr;};#endif

StrBlobPtr.cpp

#include"StrBlob.h"#include"StrBlobPtr.h"shared_ptr<vector<string>> StrBlobPtr::check(size_t i, const string& msg) const{    shared_ptr<vector<string>> ret=wptr.lock();    if(!ret)        throw runtime_error("unbound StrBlobPtr");    if(i>=ret->size())        throw out_of_range(msg);    return ret;}string& StrBlobPtr::deref() const{    auto ret=check(curr,"deference");    return (*ret)[curr];}StrBlobPtr& StrBlobPtr::incr(){    check(curr,"increment");    ++curr;    return *this;}

main.cpp

#include "TextQuery.h"#include "QueryResult.h"#include"StrBlob.h"void runQueries(StrBlob &Str){    // infile is an ifstream that is the file we want to query    TextQuery tq(Str);  // store the file and build the query map    // iterate with the user: prompt for a word to find and print results    while (true) {        cout << "enter word to look for, or q to quit: ";        string s;        // stop if we hit end-of-file on the input or if a ‘q‘ is entered        if (!(cin >> s) || s == "q") break;        // run the query and print the results        print(cout, tq.query(s)) << endl;    }}// program takes single argument specifying the file to queryint main(int argc, char **argv){    // open the file from which user will query words    ifstream infile("1.txt");    // open returns void, so we use the comma operator XREF(commaOp)    // to check the state of infile after the open    StrBlob Str;    string tmp;    while(getline(infile,tmp))    {        Str.push_back(tmp);    }    runQueries(Str);    return 0;}

1.txt

Alice Emma has long flowing red hair.Her Daddy says when the wind blowsthrough her hair, it looks almost alive,like a fiery bird in flight.A beautiful fiery bird, he tells her,magical but untamed."Daddy, shush, there is no such thing,"she tells him, at the same time wantinghim to tell her more.Shyly, she asks, "I mean, Daddy, is there?"Alice Emma has long flowing red hair.Her Daddy says when the wind blowsthrough her hair, it looks almost alive,like a fiery bird in flight.A beautiful fiery bird, he tells her,magical but untamed."Daddy, shush, there is no such thing,"she tells him, at the same time wantinghim to tell her more.Shyly, she asks, "I mean, Daddy, is there?"Alice Emma has long flowing red hair.Her Daddy says when the wind blowsthrough her hair, it looks almost alive,like a fiery bird in flight.A beautiful fiery bird, he tells her,magical but untamed."Daddy, shush, there is no such thing,"she tells him, at the same time wantinghim to tell her more.Shyly, she asks, "I mean, Daddy, is there?"