Hi i am reading an example of class implementation but getting some errors. First i am writing the code(with corresponding file names) and then i will write the errors and then my doubts. Below are the different files.
- MAINFILE.cpp
#include "textquery.h"
#include "queryresult.h"
#include<iostream>
#include<string>
#include<fstream>
void runQueries(std::ifstream &infile){
TextQuery tq(infile);
while(true){
std::cout<<"enter word to look for, or q to quit:";
std::string s;
if(!(std::cin>>s)|| s=="q")break;
print(std::cout, tq.query(s))<<std::endl;
}
}
int main(){
return 0;
}
- textquery.h
#ifndef TEXTQUERY_H
#define TEXTQUERY_H
#include<iostream>
#include<memory>
#include<string>
#include<fstream>
#include<iterator>
#include<vector>
#include<map>
#include<set>
#include<sstream>
class QueryResult;
class TextQuery {
public:
using line_no = std::vector<std::string>::size_type;
TextQuery(std::ifstream&);
QueryResult query(const std::string&) const;
private:
std::shared_ptr<std::vector<std::string>> file;//input file
std::map<std::string, std::shared_ptr<std::set<line_no>>> wm;
};
#endif
- textquery.cpp
#include "textquery.h"
#include "queryresult.h"
TextQuery::TextQuery(std::ifstream& is): file(new std::vector<std::string>){
std::string text;
while(std::getline(is, text)){
file->push_back(text);
int n = file->size() -1;
std::istringstream line(text);
std::string word;
while (line >> word){
auto &lines = wm[word];
if(!lines){
lines.reset(new std::set<line_no>);
}
lines->insert(n);
}
}
}
QueryResult TextQuery::query(const std::string &sought) const{
static std::shared_ptr<std::set<TextQuery::line_no>> nodata(new std::set<line_no>);
std::map<std::string,std::shared_ptr<std::set<TextQuery::line_no>>>::const_iterator loc = wm.find(sought);
if(loc == wm.end()){
return QueryResult(sought, nodata, file);//not found
}
else {
return QueryResult(sought, loc->second, file);
}
}
- queryresult.h
#ifndef QUERYRESULT_H
#define QUERYRESULT_H
#include<iostream>
#include<memory>
#include<string>
#include<fstream>
#include<iterator>
#include<vector>
#include<map>
#include<set>
class QueryResult {
friend std::ostream& print(std::ostream&, const QueryResult&);
public:
using line_no = std::vector<std::string>::size_type;
QueryResult(std::string s, std::shared_ptr<std::set<line_no>> p, std::shared_ptr<std::vector<std::string>> f)
:sought(s), lines(p), file(f) {
}
private:
std::string sought;
std::shared_ptr<std::set<line_no>> lines;
std::shared_ptr<std::vector<std::string>> file;
};
std::ostream& print(std::ostream&, const QueryResult&);
#endif
- queryresult.cpp
#include "queryresult.h"
std::ostream& print(std::ostream& os, const QueryResult& qr){
os << qr.sought << " occurs " << qr.lines->size() << " "<< make_plural(qr.lines->size(), "time", "s")<< std::endl;
for(auto num: *qr.lines)//for every element in the set
{
os<< "\t(line"<<num+1<<")"<<*(qr.file->begin() + num)<<std::endl;
}
return os;
}
std::string make_plural(std::size_t ctr, const std::string &word, const std::string &ending){
return (ctr >1) ? word + ending : word;
}
Now the error i am getting are:
/tmp/ccpkNtoM.o: In function runQueries(std::basic_ifstream<char, std::char_traits<char> >&)': MAINFILE.cpp:(.text+0xdd): undefined reference to TextQuery::TextQuery(std::basic_ifstream<char, std::char_traits >&)' MAINFILE.cpp:(.text+0x170): undefined reference to TextQuery::query(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) const' MAINFILE.cpp:(.text+0x183): undefined reference to print(std::ostream&, QueryResult const&)' collect2: error: ld returned 1 exit status
My questions(doubts) are as follows :
- How can i resolve these erros and why i am getting those even though i have defined the corresponding functions.
- As you can see in the textquery.cpp file i have defined a variable
locof typestd::map<std::string,std::shared_ptr<std::set<TextQuery::line_no>>>::const_iteratorusingwm.find(sought);. But when i try to change theconst_iteratortoiteratorin the above line it gives error. Why can't i usestd::map<std::string,std::shared_ptr<std::set<TextQuery::line_no>>>::iterator=wm.find(sought). I know that find() function returns either an iterator or a const_iterator but why in our program it is returning const_iterator instead of iterator?
Aucun commentaire:
Enregistrer un commentaire