当前位置: 首页 > news >正文

CCF CSP 第33次(2024.03)(2_相似度计算_C++)(字符串中字母大小写转换+哈希集合)

CCF CSP 第33次(2024.03)(2_相似度计算_C++)

    • 题目背景:
    • 题目描述:
    • 输入格式:
    • 输出格式:
    • 样例1输入:
    • 样例1输出:
    • 样例1解释:
    • 样例2输入:
    • 样例2输出:
    • 样例2解释:
    • 样例3输入:
    • 样例3输出:
    • 子任务:
      • 解题思路:
        • 思路一(字符串中字母大小写转换+哈希集合):
      • 代码实现
        • 代码实现(思路一(字符串中字母大小写转换+哈希集合)):

时间限制: 1.0 秒
空间限制: 512 MiB

题目背景:

两个集合的 Jaccard 相似度定义为:
Sim(A,B)= ∣A∪B∣/∣A∩B∣
​即交集的大小除以并集的大小。当集合 𝐴 和 𝐵完全相同时,𝑆𝑖𝑚(𝐴,𝐵)=1取得最大值;当二者交集为空时,𝑆𝑖𝑚(𝐴,𝐵)=0取得最小值。

题目描述:

除了进行简单的词频统计,小 P 还希望使用 Jaccard 相似度来评估两篇文章的相似性。 具体来说,每篇文章均由若干个英文单词组成,且英文单词仅包含“大小写英文字母”。 对于给定的两篇文章,小 P 首先需要提取出两者的单词集合 𝐴和 𝐵,即去掉各自重复的单词。 然后计算出:

∣𝐴∩𝐵∣,即有多少个不同的单词同时出现在两篇文章中;
∣𝐴∪𝐵∣,即两篇文章一共包含了多少个不同的单词。
最后再将两者相除即可算出相似度。 需要注意,在整个计算过程中应当忽略英文字母大小写的区别,比如 the、The 和 THE 三者都应被视作同一个单词。

试编写程序帮助小 P 完成前两步,计算出 ∣𝐴∩𝐵∣ 和 ∣𝐴∪𝐵∣;小 P 将亲自完成最后一步的除法运算。

输入格式:

从标准输入读入数据。

输入共三行。

输入的第一行包含两个正整数 𝑛 和 𝑚,分别表示两篇文章的单词个数。

第二行包含空格分隔的 𝑛 个单词,表示第一篇文章;

第三行包含空格分隔的 𝑚 个单词,表示第二篇文章。

输出格式:

输出到标准输出。

输出共两行。

第一行输出一个整数 ∣𝐴∩𝐵∣,即有多少个不同的单词同时出现在两篇文章中;

第二行输出一个整数 ∣𝐴∪𝐵∣,即两篇文章一共包含了多少个不同的单词。

样例1输入:

3 2
The tHe thE
the THE

样例1输出:

1
1

样例1解释:

𝐴=𝐵=𝐴∩𝐵=𝐴∪𝐵= {the}

样例2输入:

9 7
Par les soirs bleus dete jirai dans les sentiers
PICOTE PAR LES BLES FOULER LHERBE MENUE

样例2输出:

2
13

样例2解释:

𝐴=A= {bleus, dans, dete, jirai, les, par, sentiers, soirs} ∣𝐴∣=8

𝐵=B= {bles, fouler, les, lherbe, menue, par, picote} ∣𝐵∣=7

𝐴∩𝐵=A∩B= {les, par} ∣𝐴∩𝐵∣=2

样例3输入:

15 15
Thou that art now the worlds fresh ornament And only herald to the gaudy spring
Shall I compare thee to a summers day Thou art more lovely and more temperate

样例3输出:

4
24

子任务:

80% 的测试数据满足:𝑛,𝑚≤100且所有字母均为小写;

全部的测试数据满足:𝑛,𝑚≤104 且每个单词最多包含 10 个字母。

解题思路:

思路一(字符串中字母大小写转换+哈希集合):

1、解题步骤拆分:
① 忽略英文字母大小写,我们可以将所有的字母转换为小写。
② 忽略一个集合中重复的单词,我们可以想到哈希集合来进行降重。
③ 求并集,可以想到将两个集合中的并入一个集合。
④ 求交集,可以想到通过查找集合A中的元素是否存在集合B中来求出。

代码实现

代码实现(思路一(字符串中字母大小写转换+哈希集合)):
#include<iostream>  
#include<unordered_set>  // 引入unordered_set容器,使用哈希表来存储不重复元素
#include<algorithm>   // 引入算法库,包含transform、tolower、toupper等函数using namespace std;int main(int argc, char const *argv[]) {int n, m;cin >> n >> m;  // 输入两个整数 n 和 m,分别表示集合A和集合B的元素个数unordered_set<string> setA, setB;  // 定义两个unordered_set,分别存储集合A和集合B的元素string word;  // 用于存储每次输入的单词// 读取n个单词并插入集合setAfor (int i = 0; i < n; i++) {cin >> word;// 使用transform函数将单词转为小写  //tolower转小写 。toupper转为大写transform(word.begin(), word.end(), word.begin(), ::tolower);  // tolower将字母转为小写setA.insert(word);  // 将小写形式的单词插入setA}// 读取m个单词并插入集合setBfor (int i = 0; i < m; i++) {cin >> word;// 使用transform函数将单词转为小写transform(word.begin(), word.end(), word.begin(), ::tolower);  // tolower将字母转为小写setB.insert(word);  // 将小写形式的单词插入setB}unordered_set<string> intersection, unionSet;  // 定义两个unordered_set,分别存储交集和并集// 计算集合B与集合A的交集 (也可以使用一个变量来计数)for (auto &str : setB) {  // 遍历集合B中的每个元素if (setA.count(str)) {  // 如果setA中包含该元素  //如果使用setA.find()则需与setA.end()进行比较判断有无intersection.insert(str);  // 将该元素插入交集}}// 计算集合A与集合B的并集(也可以使用原来的set集合,将setB并入setA)unionSet = setA;  // 将setA的所有元素先复制到unionSet中for (auto &str : setB) {  // 遍历集合B中的每个元素unionSet.insert(str);  // 将集合B中的元素插入unionSet(如果元素已经存在,insert不会重复插入)}// 输出交集的大小cout << intersection.size() << endl;// 输出并集的大小cout << unionSet.size() << endl;return 0;  // 返回0,表示程序成功结束
}
//ch = std::toupper(ch);  // 将字符转换为大写

欢迎大家和我沟通交流(✿◠‿◠)


http://www.mrgr.cn/news/96031.html

相关文章:

  • 【软件测试】:软件测试实战
  • 3.26[a]paracompute homework
  • vue遗漏的知识点(动态组件.)
  • openpnp,cadence SPB17.4,placement - 从allegro中导出坐标文件的选项会影响贴片精度
  • PyTorch处理数据--Dataset和DataLoader
  • 详解java体系实用知识总结
  • K8S学习之基础五十二:k8s配置jenkins
  • 我的世界1.20.1forge模组进阶开发教程——结构(3)
  • 我的世界进阶教程——结构(2)
  • 【C++网络编程】番外篇(实战):基于Boost.Asio协程的HTTP服务器实现与静态文件服务开发指南
  • macOS 制作dmg磁盘映像安装包
  • 2.0 项目管理前言
  • 车载以太网网络测试 -24【SOME/IP概述】
  • 科普:特征、规则、模型,及Lift(提升度)
  • PyTorch图像预处理--Compose
  • Linux面试题
  • 优选算法系列(4.前缀和 _下) k
  • CAS(Compare And Swap)
  • 23种设计模式-观察者(Observer)设计模式
  • ElasticSearch -- 部署完整步骤