C++ 实现类似Notepad++ Ctrl+F 的搜索功能

本文介绍了如何使用C++实现类似Notepad++的Ctrl+F搜索功能,包括查找单词、非匹配、或匹配、与匹配等查询方式,并展示了不同查询阶段的实现与测试代码。
摘要由CSDN通过智能技术生成

<span style="font-family: Arial, Helvetica, sans-serif; background-color: rgb(255, 255, 255);">《C++ Primer》  10.6 节讲的是容器的综合应用:文本查询程序</span>

该功能是就是平常大家非常爱使用的ctrl +F 功能的原型, 本文给出和Notepad++ 搜索功能完全一样的实现


阶段一:命令行下实现查找某个单词

需求:读取用户指定的任意文本,允许用户从该文件中查找单词。查询的结果是该单词出现的次数,并列出每次出现所在的行。如果一个单词在同一行中多次出现,程序将只显示该行一次。行号按升序显示。

可能的输出结果:

element occurs 125 times

(line 62) element with a given key.

(line 64) second element with the same key

(lien 153) element |==| operator.

(line 250) the element type

(line 398)corresponding elemnet

//后面省略了120行


实现& 测试代码:

#include <iostream>
#include <iterator>
#include <algorithm>
#include <fstream>
#include <list>
#include <string>
#include <vector>
#include <set>
#include<utility>
#include<functional>
#include<stdexcept>
#include<map>
#include<sstream>

class TextQuery
{
public:
    typedef std::vector<std::string>::size_type line_no;
    /* interface:
    read_file builds internal data structures for the given file
    run_query finds the given word and returns set of lines on while it appears
    test_line return a  requested line from the input file
    */
    void read_file(std::ifstream & is)
    {
        store_file(is);
        build_map();
    }

    std::set<line_no> run_query(const std::string& );
    std::string test_line(line_no ) const;
private:
    //utility function used by read_file
    void store_file(std::ifstream&);
    //associated each word with a set of line members
    void build_map();
    //vector to store input file
    std::vector<std::string> lines_of_text;
    //map word to set of lines on which it occurs
    std::map< std::string,std::set<line_no> > word_map;
};


std::set<TextQuery::line_no> TextQuery::run_query(const std::string& query_word)
{
    return word_map[query_word];
}


 std::string TextQuery::test_line(line_no l) const
 {
     return lines_of_text[l];
 }



void TextQuery::store_file(std::ifstream&  infile)
{
    std::string temp;
    while(std::getline(infile,temp))
    {
        lines_of_text.push_back(temp);
    }

}

void TextQuery::build_map()
{

    std::string temp;
    for(line_no l = 0;  l != lines_of_text.size();  ++l)
    {

        std::stringstream ss;
        ss << lines_of_text[l];
        while( ss >> temp)
        {
            if(word_map.count(temp))
            {
                word_map[temp].insert(l);
            }
            else
            {
                std::set<line_no> temp_set;
                temp_set.insert(l);
                word_map.insert(std::make_pair(temp,temp_set));
            }

        }
    }



}




void print_results(const std::set<TextQuery::line_no>& locs,const std::string & query_key,const TextQuery &tq)
{
    std::set<TextQuery::line_no>::size_type occur_times = locs.size();

    std::cout<<query_key<<" occurs "<<occur_times<<" times"<<std::endl;

    for(std::set<TextQuery::line_no>::const_iterator  i= locs.begin() ;   i != locs.end() ; ++i)
    {
        std::cout<<"(line "<<(*i)+1<<" ) "
                << tq.test_line( *i )<<std::endl;
    }
}






//test code
int main()
{
    std::ifstream infile;
    infile.open("test.txt");

    TextQuery tq;
    tq.read_file(infile);


    while(true)
    {
        std::cout<<"enter a word to look for,or q to quit: "<<std::endl;
        std::string s;
        std::cin >> s;
        if(!std::cin || s =="q")
            break;
        std::set<TextQuery::line_no> locs = tq.run_query(s);

        print_results(locs,s,tq);
    }


    return 0;

}




运行结果:

输入文件内容:

Welcome to the newToCpp wiki! 
In this github ,i put some learning exercises i've done while learning C++.
The books i used to learn C++ are: 
C++ Primer Effective C++ More Effective C++ Effective STL Exceptional C++ More E
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值