数据结构作业——寻人启事(字符串哈希)
寻人启事
Description
才来到福州大学的你很想要知道你几位失散多年的朋友是否也来到了福州 大学,于是你黑进了学校的学籍管理系统,但无奈里面的记录太多了,想通过一 条条比对查找他们的信息过于麻烦, 现在你决定写一个程序帮助你加快查找速度。
Input
第一行输入包括 n、m 两个数字,表示学籍系统里共 n(n<=1000000)条记 录,m(m<=1000 且 m<=n)个你想要寻找的朋友。接下来 n 行每行一个长度不 超过 5 的名字代表这个人的名字,在接下来 m 行每行一个长度不超过 5 的名字 代表想要寻找的人的名字。
Output
输出一个整数 k,代表学校中朋友的数量。
Sample Input
3 2
Tom
Alice
Jack
Jack
Ted
Sample Output
1
HINT
系统里的名字没有重复。
待查询的名字没有重复。
思路
简单的hash题,冲突利用分离链表法解决,并且用邻接表代替链表。主要在于hash函数的构造,一开始构造了个简单的hash函数,导致冲突过多,速度很慢,后来换了Horner法则构造,冲突极大的减少。
AC代码
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 | #include<cstdio> #include<cstring> #include<iostream> using namespace std; const int mod = 999983; const int maxn = 1000005; char str[maxn][10]; int tot = 0,head[mod+5],next[maxn]; int IndexHash( char *key) //Hormer法则 { int hashval = 0; while (*key != '\0' ) hashval = (hashval<<5) + *key++; return hashval % mod; } void addnode( int hashval) { next[tot] = head[hashval]; head[hashval] = tot++; } int main() { //freopen("data.txt","r",stdin); //freopen("2.txt","w",stdout); int n,m,i,cnt = 0; char tmp[10]; memset (str,0, sizeof (str)); memset (head,-1, sizeof (head)); scanf ( "%d%d" ,&n,&m); for (i = 0;i < n;i++) { scanf ( "%s" ,str[i]); int hashval = IndexHash(str[i]); addnode(hashval); } while (m--) { scanf ( "%s" ,tmp); int hashval = IndexHash(tmp); for (i = head[hashval];i != -1;i = next[i]) { if ( strcmp (tmp,str[i]) == 0) cnt++; } } printf ( "%d\n" ,cnt); return 0; } |
对拍程序
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 | #include<iostream> #include<cstdio> #include<cstdlib> #include<cstring> #include<ctime> #include<map> #include<string> using namespace std; const int maxn = 1000000; int main() { freopen ( "data.txt" , "w" ,stdout); srand ( time (NULL)); map<string, int >mp1,mp2; map<string, int >::iterator it; int n = maxn,m = rand ()%n; printf ( "%d %d\n" ,n,m); for ( int i = 0;i < n;) { string str; int len = rand ()%5 + 1; while (len--) str += rand ()%58 + 'A' ; it = mp1.find(str); if (it == mp1.end()) cout << str << endl,i++; mp1[str] = 1; } for ( int i = 0;i < m;) { string str; int len = rand ()%5 + 1; while (len--) str += rand ()%58 + 'A' ; it = mp2.find(str); if (it == mp2.end()) cout << str << endl,i++; mp2[str] = 1; } return 0; } |
┆ 凉 ┆ 暖 ┆ 降 ┆ 等 ┆ 幸 ┆ 我 ┆ 我 ┆ 里 ┆ 将 ┆ ┆ 可 ┆ 有 ┆ 谦 ┆ 戮 ┆ 那 ┆ ┆ 大 ┆ ┆ 始 ┆ 然 ┆
┆ 薄 ┆ 一 ┆ 临 ┆ 你 ┆ 的 ┆ 还 ┆ 没 ┆ ┆ 来 ┆ ┆ 是 ┆ 来 ┆ 逊 ┆ 没 ┆ 些 ┆ ┆ 雁 ┆ ┆ 终 ┆ 而 ┆
┆ ┆ 暖 ┆ ┆ 如 ┆ 地 ┆ 站 ┆ 有 ┆ ┆ 也 ┆ ┆ 我 ┆ ┆ 的 ┆ 有 ┆ 精 ┆ ┆ 也 ┆ ┆ 没 ┆ 你 ┆
┆ ┆ 这 ┆ ┆ 试 ┆ 方 ┆ 在 ┆ 逃 ┆ ┆ 会 ┆ ┆ 在 ┆ ┆ 清 ┆ 来 ┆ 准 ┆ ┆ 没 ┆ ┆ 有 ┆ 没 ┆
┆ ┆ 生 ┆ ┆ 探 ┆ ┆ 最 ┆ 避 ┆ ┆ 在 ┆ ┆ 这 ┆ ┆ 晨 ┆ ┆ 的 ┆ ┆ 有 ┆ ┆ 来 ┆ 有 ┆
┆ ┆ 之 ┆ ┆ 般 ┆ ┆ 不 ┆ ┆ ┆ 这 ┆ ┆ 里 ┆ ┆ 没 ┆ ┆ 杀 ┆ ┆ 来 ┆ ┆ ┆ 来 ┆
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 别再用vector<bool>了!Google高级工程师:这可能是STL最大的设计失误
· 单元测试从入门到精通
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 上周热点回顾(3.3-3.9)