开启辅助访问 切换到宽版

精易论坛

 找回密码
 注册

QQ登录

只需一步,快速开始

用微信号发送消息登录论坛

新人指南 邀请好友注册 - 我关注人的新帖 教你赚取精币 - 每日签到


求职/招聘- 论坛接单- 开发者大厅

论坛版规 总版规 - 建议/投诉 - 应聘版主 - 精华帖总集 积分说明 - 禁言标准 - 有奖举报

查看: 1355|回复: 45
收起左侧

[易语言纯源码] 文本_哈希去重独立版,1000万条只需5秒

[复制链接]
发表于 2024-11-10 07:46:16 | 显示全部楼层 |阅读模式   广东省深圳市
分享源码
界面截图:
是否带模块: 纯源码
备注说明: -
本帖最后由 梦幻1096 于 2024-11-10 14:00 编辑
  
子程序名返回值类型公开备 注
文本_哈希去重整数型 如果测试速度,请编译后测试,调试的话申请释放内存会很慢,太大的数据可能直接卡死  by梦幻1096 Q:1096194951
参数名类 型参考可空数组备 注
文本数组文本型
变量名类 型静态数组备 注
链表地址整数型 
链表长度整数型 
键数量整数型 
预设内存大小整数型 
预设内存指针整数型 
申请内存记录整数型0
扩容触发点整数型 
表位置整数型 
链表节点整数型 
节点地址整数型 
文本地址整数型 
文本长度整数型 
哈希值整数型 
是否重复逻辑型 
a整数型 
b整数型 
c整数型 
d整数型 
e整数型 
f整数型 
i整数型 
j整数型 
' 完全采用易代码写的哈希表去重方式,未使用任何模块,效率还可以
如果真 (取数组成员数 (文本数组) ≤ 1)
返回 (取数组成员数 (文本数组))
' 定义表初始长度
链表长度 = 16
' 申请表的起始地址内存
链表地址 = 申请内存 (左移 (链表长度, 2), )
' 如果数组很大的话,比如10000+,预先申请一片内存区域,这里默认给了10000,不要设置太小就行了,10000内本来就很快
如果真 (取数组成员数 (文本数组) > 10000)
预设内存大小 = 取数组成员数 (文本数组) × 4
加入成员 (申请内存记录, 申请内存 (预设内存大小, ))
预设内存指针 = 申请内存记录 [1]

' 定义扩容触发点,负载因子为0.75自动扩容
扩容触发点 = 链表长度 × 0.75
' 循环添加文本键
计次循环首 (取数组成员数 (文本数组), i)
' 取文本长度如果有更快的版本,可自行替换
文本地址 = 取变量数据地址 (文本数组 [i])
如果真 (文本地址 = 0)
到循环尾 ()
文本长度 = 取文本长度 (文本数组 [i])
' 取哈希值
c = 文本长度 \ 4
d = 文本长度 % 4
a = 十六进制 (“811c9dc5”)
b = 十六进制 (“01000193”)
e = 文本地址
如果真 (c ≠ 0)
计次循环首 (c, j)
f = 指针到整数 (e)
a = 位异或 (a, f) × b
e = e + 4
计次循环尾 ()
如果真 (d ≠ 0)
f = 左移 (指针到整数 (e), (4 - d) × 8)
a = 位异或 (a, f) × b
哈希值 = 取绝对值 (a)
' 取哈希值的余数获取表位置
表位置 = 哈希值 (链表长度 - 1) + 1
' 起始地址+表位置*4 为哈希值获取到的位置,从当前位置获取节点地址
链表节点 = 链表地址 + 左移 (表位置, 2)
节点地址 = 指针到整数 (链表节点)
' 获取到节点地址开始遍历节点
判断循环首 (节点地址 ≠ 0)
如果真 (哈希值 = 指针到整数 (节点地址))  ' 节点首地址为哈希值 如果哈希值相同则继续判断长度
如果真 (文本长度 = 指针到整数 (节点地址 + 8))  ' 节点地址+8 为长度 如果长度相同,则对比数据
如果真 (文本数组 [i] = 文本数组 [指针到整数 (节点地址 + 12)])  ' 节点地址+12 为文本下标,如果速度更快的对比方式可自行替换
是否重复 = 真
跳出循环 ()
' 对比结果如果完全相同,则表示数据重复,直接跳出去循环下一条


链表节点 = 节点地址 + 4  ' 节点地址+4为下一节点地址存放处
节点地址 = 指针到整数 (链表节点)  ' 读下一节点地址,继续循环,直到节点地址=0
判断循环尾 ()
如果真 (是否重复 = )
是否重复 = 假
到循环尾 ()

' 经过上面对比,节点地址肯定=0 所以申请一个新地址为节点地址
如果 (预设内存指针 = 0)
节点地址 = 申请内存 (16, )  ' 节点为16字节长度
加入成员 (申请内存记录, 节点地址)  ' 将申请的指针保存起来,以便后面释放


' 如果在程序开始预设了内存,则这里分配之前申请好的内存并更新指针
如果真 (预设内存大小 < 16)
预设内存大小 = 取数组成员数 (文本数组) × 4
加入成员 (申请内存记录, 申请内存 (预设内存大小, ))
预设内存指针 = 申请内存记录 [取数组成员数 (申请内存记录)]
节点地址 = 预设内存指针
预设内存指针 = 预设内存指针 + 16
预设内存大小 = 预设内存大小 - 16

写到内存 (节点地址, 链表节点, )  ' 将新申请的地址与上一节点连接上
' 以下为链表结构
' 0 哈希值
' 4 下一节点指针,由于是新申请的,所以没有下一节点,留空
' 8 保存长度,以便于后面对比
' 12 保存下标,用作后面对比
写到内存 (哈希值, 节点地址, )
写到内存 (文本长度, 节点地址 + 8, )
' 将键数量递增,以便触发扩容
键数量 = 键数量 + 1
如果真 (键数量 ≠ i)
' 将未重复的数组指针交换到当前键数量下标,就是把他放到前面去
交换变量 (文本数组 [键数量], 文本数组 [i])
写到内存 (键数量, 节点地址 + 12, )
' 下面为扩容程序
如果真 (键数量 ≥ 扩容触发点)
j = 左移 (链表长度, 1)
f = 申请内存 (左移 (j, 2), )
变量循环首 (链表地址, 链表地址 + 左移 (链表长度 - 1, 2), 4, c)
e = 指针到整数 (c)
判断循环首 (e ≠ 0)
哈希值 = 指针到整数 (e)
表位置 = 哈希值 (j - 1) + 1
a = f + 左移 (表位置, 2)
b = 指针到整数 (a)
判断循环首 (b ≠ 0)
a = b + 4
b = 指针到整数 (a)
判断循环尾 ()
写到内存 (e, a, )
c = e + 4
e = 指针到整数 (c)
写到内存 (0, c, )
判断循环尾 ()
变量循环尾 ()
' 释放旧链表
释放内存 (链表地址)
链表地址 = f
链表长度 = j
扩容触发点 = 链表长度 × 0.75

计次循环尾 ()
' 搞定,释放之前申请的全部内存
计次循环首 (取数组成员数 (申请内存记录), i)
释放内存 (申请内存记录 [i])
计次循环尾 ()
' 最后释放链表地址
释放内存 (链表地址)
' 由于之前把不重复的都放到了数组前面,这里直接重定义数组为键数量就行了
重定义数组 (文本数组, 真, 键数量)
返回 (键数量)


i支持库列表   支持库注释   
spec特殊功能支持库

纯的不能再纯的源码,完全用的易语言代码的方式写的,效率挺高的,1000万只需5秒,不过说是这么说,但是单条文本太长的话就要慢一些,总之比一般的去重都要快很多吧,而且这个是独立为1个子程序的,不需要什么模块 DLL啥的,写了我几个小时,免费分享给你们吧!有啥问题bug啥的评论区留言!
将保存文本数据改成了保存文本指针,减少了内存开销!,修复了文本指针为0(也就是数组里面存在空文本的情况)
又又又更新了一下,将保存文本指针改成保存文本下标,效率又可以提升不少!



文本_哈希去重.e

12.48 KB, 下载次数: 74, 下载积分: 精币 -2 枚

点评

时间长了之后,才会深刻体验到,写法牛逼只是第二层,算法牛逼才是大气层   上海市上海市  发表于 2024-11-11 19:03

评分

参与人数 11好评 +6 精币 +23 收起 理由
wa690602724 + 1 感谢分享,很给力!~
光影魔术 + 2 开源精神必须支持~
wjswzj0 + 1 + 1 100Wy以上的数据,去重后的成员数都是32768???
kyo9766 + 1 感谢分享,很给力!~
笨来无一悟 + 1 + 3 纯情渣男 功德无量
cqcc + 3 支持开源~!感谢分享
1355301564 + 2 YYDS~!
喵帕斯和艾希 + 1 + 3 支持开源~!感谢分享
xf702 + 1 + 3 感谢分享,很给力!~
ChinaSaga + 1 + 2 开源精神必须支持~
tan666 + 1 + 2 支持开源~!感谢分享

查看全部评分


本帖被以下淘专辑推荐:

签到天数: 2 天

发表于 7 天前 | 显示全部楼层   江苏省苏州市
进来看看
回复 支持 反对

使用道具 举报

签到天数: 20 天

发表于 2024-11-14 18:38:39 | 显示全部楼层   重庆市重庆市
这个是真牛逼
回复 支持 反对

使用道具 举报

结帖率:100% (1/1)

签到天数: 13 天

发表于 2024-11-12 22:03:04 | 显示全部楼层   广西壮族自治区柳州市
感谢分享源码
回复 支持 反对

使用道具 举报

结帖率:100% (13/13)

签到天数: 19 天

发表于 2024-11-12 19:48:56 | 显示全部楼层   广东省江门市
感谢分享,很给力!~
回复 支持 反对

使用道具 举报

签到天数: 5 天

发表于 2024-11-12 15:43:15 | 显示全部楼层   浙江省温州市
感谢分享,很给力!~
回复 支持 反对

使用道具 举报

签到天数: 20 天

发表于 2024-11-12 11:43:48 | 显示全部楼层   吉林省延边朝鲜族自治州
回复 支持 反对

使用道具 举报

结帖率:90% (9/10)

签到天数: 13 天

发表于 2024-11-12 09:44:28 | 显示全部楼层   山东省菏泽市
感谢分享,支持开源!!!
回复 支持 反对

使用道具 举报

签到天数: 21 天

发表于 2024-11-12 09:38:23 | 显示全部楼层   浙江省宁波市
感谢分享,支持开源!!!
回复 支持 反对

使用道具 举报

结帖率:100% (4/4)

签到天数: 22 天

发表于 2024-11-11 18:23:20 | 显示全部楼层   山东省淄博市
感谢分享
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则 致发广告者

发布主题 收藏帖子 返回列表

sitemap| 易语言源码| 易语言教程| 易语言论坛| 易语言模块| 手机版| 广告投放| 精易论坛
拒绝任何人以任何形式在本论坛发表与中华人民共和国法律相抵触的言论,本站内容均为会员发表,并不代表精易立场!
论坛帖子内容仅用于技术交流学习和研究的目的,严禁用于非法目的,否则造成一切后果自负!如帖子内容侵害到你的权益,请联系我们!
防范网络诈骗,远离网络犯罪 违法和不良信息举报电话0663-3422125,QQ: 793400750,邮箱:wp@125.la
Powered by Discuz! X3.4 揭阳市揭东区精易科技有限公司 ( 粤ICP备12094385号-1) 粤公网安备 44522102000125 增值电信业务经营许可证 粤B2-20192173

快速回复 返回顶部 返回列表