pat1022Digital Library (30)

本文介绍了一个图书信息检索系统的实现方案,通过结构体封装图书信息,并利用map进行高效的关键字检索。文章详细阐述了如何处理图书数据输入、排序及查询过程。

题意分析:

(1)给出若干条书籍信息:按照书名、作者、关键字、出版商、出版年份的格式列出;再给出若干条检索记录,这些检索记录是围绕书名、作者、关键字、出版社以及年份,来按顺序列出查询的书的ID,考察的是排序和查找。

(2)将书的信息包装成结构体,在这些结构体当中,比较容易检索的包括书名、作者、出版社、出版年份;而对于关键字来说,由于每本书最多会有5个关键字,书的数目比较大时,如果将关键字向量或数组维护在结构体当中,每次都分别检索,检索的效率就可又能降低;因此聪明的大家也可能想到了将关键字分离出来,单独处理,按关键字的检索使用map效率会很高,而同一个关键字有可能会检索到多本书籍,所以map按关键字检索到的应该是一个书籍ID的向量

(3)也可以将书籍的各信息分开存储到map当中,但是这样又引来另外一个问题,那就是需要对每一项查询记录结果排序,额外增加了负担;这里就体现出了包装结构体的优势:只需要排序一次

可能坑点:

(1)将关键字也维护在结构体当中,导致检索超时

#include <iostream>
#include <algorithm>
#include <string.h>
#include <sstream>
#include <map>
#include <vector>
#include <stdio.h>
using namespace std;
struct bookInfo
{
    string ID;
    string title;
    string author;
    string publisher;
    string year;
};
bookInfo book[10001];
map<string,vector<string> >keymap;
bool cmp(bookInfo a,bookInfo b)
{
    return a.ID<b.ID;
}
int main()
{
    int N,i=0;
    cin>>N;
    string keyword,temp;
    while(i<N)
    {
        cin>>book[i].ID;
        getchar();
        getline(cin,book[i].title,'\n');
        getline(cin,book[i].author,'\n');
        getline(cin,keyword,'\n');
        istringstream is(keyword);
        while(is>>temp)keymap[temp].push_back(book[i].ID);
        getline(cin,book[i].publisher,'\n');
        getline(cin,book[i].year,'\n');
        i++;
    }
    sort(&book[0],&book[N],cmp);
    int M;
    cin>>M;
    int j=0;
    int index;
    string query;
    int flag;
    while(j<M)
    {
        flag=0;
        scanf("%d: ",&index);
        getline(cin,query,'\n');
        cout<<index<<": "<<query<<endl;
        if(index==1)
        {
            for(int k=0;k<N;k++)
            {
                if(book[k].title==query)
                {
                    flag=1;
                    cout<<book[k].ID<<endl;
                }
            }
        }
        else if(index==2)
        {
            for(int k=0;k<N;k++)
            {
                if(book[k].author==query)
                {
                    flag=1;
                    cout<<book[k].ID<<endl;
                }
            }
        }
        else if(index==3)
        {
            sort(keymap[query].begin(),keymap[query].end());
            if(keymap[query].size()>0)
            {
                flag=1;
                vector<string >::iterator iter=keymap[query].begin();
                for(;iter!=keymap[query].end();iter++)
                {
                    cout<<*iter<<endl;
                }
            }
        }
        else if(index==4)
        {
            for(int k=0;k<N;k++)
            {
                if(book[k].publisher==query)
                {
                    flag=1;
                    cout<<book[k].ID<<endl;
                }
            }
        }
        else
        {
            for(int k=0;k<N;k++)
            {
                if(book[k].year==query)
                {
                    flag=1;
                    cout<<book[k].ID<<endl;
                }
            }
        }
        if(flag==0)cout<<"Not Found"<<endl;
        j++;
    }
    return 0;
}


### 关于 PAT 甲级真题 1172 的解析 PAT (Programming Ability Test) 是一项针对编程能力的测试,其中甲级难度较高,涉及算法设计与实现。以下是关于题目 **1172** 的相关内容。 #### 题目描述 根据已知的信息[^1]以及公开资源中的整理[^2],PAT 甲级真题 1172 被命名为《Digital Library》。该题目主要考察字符串处理、数据结构的应用以及输入输出优化等内容。具体要求如下: - 输入一系列书籍信息(包括书名、作者、关键词、出版社和出版年份),并按照指定条件查询匹配的结果。 - 查询方式分为五种: 1. 按照书名查找; 2. 按照作者查找; 3. 按照关键词查找; 4. 按照出版社查找; 5. 按照出版年份查找。 每本书籍最多被查找到一次,即使它满足多个查询条件。 --- #### 解决方案概述 为了高效解决此问题,可以采用以下方法: ##### 数据存储 定义一个 `Book` 类来表示一本书的主要属性,便于统一管理书籍信息。代码示例如下: ```cpp struct Book { int id; // 图书编号 string title; // 书名 string author; // 作者 vector<string> tags; // 关键词列表 string publisher; // 出版社 int year; // 出版年份 }; ``` ##### 处理逻辑 通过构建多关键字索引来加速查询操作。对于不同的查询类型,分别建立哈希表或其他快速检索的数据结构。例如: - 使用 `unordered_map<string, set<int>>` 存储按书名、作者、出版社等字段的映射关系。 - 对于关键词查询,则需遍历所有书籍逐一比较。 下面是完整的 C++ 实现代码片段: ```cpp #include <iostream> #include <vector> #include <string> #include <unordered_map> #include <set> using namespace std; // 定义图书结构体 struct Book { int id; string title; string author; vector<string> tags; string publisher; int year; }; int main() { int N, M; cin >> N; // 总共N本书 vector<Book> books(N); // 初始化书籍信息 for(int i=0;i<N;i++) { cin >> books[i].id >> books[i].title >> books[i].author >> books[i].tags.size(); // 假设先读取标签数量K books[i].tags.resize(books[i].tags.size()); for(auto &tag : books[i].tags){ cin >> tag; } cin >> books[i].publisher >> books[i].year; } cin >> M; // 查询次数M unordered_map<string, set<int>> titleMap, authorMap, pubMap; // 构建索引... } ``` 上述代码仅展示初始化部分,实际还需补充详细的索引创建及查询功能。 --- #### 注意事项 在开发过程中需要注意以下几个方面: - 输入规模较大时应考虑性能优化,比如减少不必要的字符串拷贝操作。 - 输出格式严格遵循样例说明,任何多余的空格或换行都会导致评测失败。 --- ###
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值