免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
123下一页
最近访问板块 发新帖
查看: 4673 | 回复: 22
打印 上一主题 下一主题

[文本处理] [求助]将文本中数据合并 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2013-04-15 16:05 |只看该作者 |倒序浏览
将文本中含有相同数据(只要有一个数据相同就行)的行合并为一行并去除重复
  1. cat test.2
  2. 2 3
  3. 8 9 10
  4. 7 8
  5. 12
  6. 3 4
  7. 6 11
  8. 5 7
  9. 8 12
复制代码
希望得到的结果
  1. cat result.2
  2. 2 3 4
  3. 8 9 10 7 5 12
  4. 6 11
复制代码
数据这样得到的
{2,3}{3,4}因为有共同数3所以合并为一行
{8,9,10}{7,8}{5,7}{12}{8,12}因为分别有共同数,7,8,12也合并为一行
而{6,11}没有与其他行有共同数,单独成行
==========================================================================
贴子以前发过 感谢 yinyuemi 的解答
但是那个帖子我的问题描述不清,导致得到的解答的结果有问题
==========================================================================
特从新贴出来,希望哪位大侠给予解答

论坛徽章:
23
15-16赛季CBA联赛之吉林
日期:2017-12-21 16:39:27白羊座
日期:2014-10-27 11:14:37申猴
日期:2014-10-23 08:36:23金牛座
日期:2014-09-30 08:26:49午马
日期:2014-09-29 09:40:16射手座
日期:2014-11-25 08:56:112015年辞旧岁徽章
日期:2015-03-03 16:54:152015年迎新春徽章
日期:2015-03-04 09:49:0315-16赛季CBA联赛之山东
日期:2017-12-21 16:39:1915-16赛季CBA联赛之广东
日期:2016-01-19 13:33:372015亚冠之山东鲁能
日期:2015-10-13 09:39:062015亚冠之西悉尼流浪者
日期:2015-09-21 08:27:57
2 [报告]
发表于 2013-04-15 16:51 |只看该作者
try:
  1. sed -n '
  2. s/.*/ & /
  3. H
  4. ${
  5.         g
  6.         :a
  7.         s/\n\([0-9 ]*\)\( [0-9]\{1,\} \)\([0-9 ]*\)\(\n\)\(.*\)\2/\4\5\1\2\3/
  8.         ta
  9.         s/^\n//p
  10. }' file
复制代码

论坛徽章:
0
3 [报告]
发表于 2013-04-15 17:42 |只看该作者
回复 2# ly5066113
非常感谢您的回复,虽然对您的代码表示看不懂,但是执行情况很好
但是我的数据量非常大,有几千行数据,用您的算法,计算的时间非常长,
计算半小时了,结果还没有出来
所以有没有办法将算法加速呢

论坛徽章:
23
15-16赛季CBA联赛之吉林
日期:2017-12-21 16:39:27白羊座
日期:2014-10-27 11:14:37申猴
日期:2014-10-23 08:36:23金牛座
日期:2014-09-30 08:26:49午马
日期:2014-09-29 09:40:16射手座
日期:2014-11-25 08:56:112015年辞旧岁徽章
日期:2015-03-03 16:54:152015年迎新春徽章
日期:2015-03-04 09:49:0315-16赛季CBA联赛之山东
日期:2017-12-21 16:39:1915-16赛季CBA联赛之广东
日期:2016-01-19 13:33:372015亚冠之山东鲁能
日期:2015-10-13 09:39:062015亚冠之西悉尼流浪者
日期:2015-09-21 08:27:57
4 [报告]
发表于 2013-04-15 18:19 |只看该作者
回复 3# debateshang


真实的数据贴几行,看看是不是会造成有死循环,否则几千行数据没理由跑那么久。

论坛徽章:
0
5 [报告]
发表于 2013-04-15 18:25 |只看该作者
回复 4# ly5066113


    data.tar.gz (78.09 KB, 下载次数: 23) 我将数据传上取了,但是请问我怎么看有没有死循环,确实计算一个小时也没有计算出来,应该是有死循环
那这说明数据有问题?

论坛徽章:
3
2015年辞旧岁徽章
日期:2015-03-03 16:54:152015年迎新春徽章
日期:2015-03-04 09:51:162015年亚洲杯之阿曼
日期:2015-04-07 20:00:59
6 [报告]
发表于 2013-04-15 20:11 |只看该作者
提示: 作者被禁止或删除 内容自动屏蔽

论坛徽章:
6
摩羯座
日期:2013-08-24 10:43:10狮子座
日期:2013-08-25 10:27:06天秤座
日期:2013-09-11 20:28:44午马
日期:2014-09-28 16:06:0015-16赛季CBA联赛之八一
日期:2016-12-19 13:55:0515-16赛季CBA联赛之天津
日期:2016-12-20 14:01:23
7 [报告]
发表于 2013-04-15 23:30 |只看该作者
  1. awk '{for(i=1;i<=NF;i++)c[NR]=$0;b[NR]=NF;++nr}END{for(k=nr;k>=2;k--){split(c[k],d);for(j=k-1;j>=1;j--){for(n=1;n<=b[k];n++)if(c[j] ~ d[n]){sub(d[n],"",c[k]);c[j]=c[j]" "c[k];b[j]=b[j]+b[k]-1;c[k]="";n=100000000;j=0}}}for(i=1;i<=nr;i++)if(c[i])print c[i]}' test.txt
复制代码

论坛徽章:
0
8 [报告]
发表于 2013-04-15 23:37 |只看该作者
本帖最后由 debateshang 于 2013-04-15 23:38 编辑

回复 7# cao627
感谢您的指点,但是程序好像有点问题
  1. cat test1
  2. 2 3 4 5 9 8
  3. 7 8
  4. 5 6
  5. 11 12
  6. 4 2 3
复制代码
  1. awk '{for(i=1;i<=NF;i++)c[NR]=$0;b[NR]=NF;++nr}END{for(k=nr;k>=2;k--){split(c[k],d);for(j=k-1;j>=1;j--){for(n=1;n<=b[k];n++)if(c[j] ~ d[n]){sub(d[n],"",c[k]);c[j]=c[j]" "c[k];b[j]=b[j]+b[k]-1;c[k]="";n=100000000;j=0}}}for(i=1;i<=nr;i++)if(c[i])print c[i]}' test1
  2. 2 3 4 5 9 8 11 12   3   6 7
复制代码
应该得到的结果
  1. 2 3 4 5 9 7 6 8
  2. 11 12
复制代码
将每一行如果有相同的元素,就去重复合并,没有就另起一行,对于每行输出的顺序没有要求

论坛徽章:
7
戌狗
日期:2013-12-15 20:43:38技术图书徽章
日期:2014-03-05 01:33:12技术图书徽章
日期:2014-03-15 20:31:17未羊
日期:2014-03-25 23:48:20丑牛
日期:2014-04-07 22:37:44巳蛇
日期:2014-04-11 21:58:0915-16赛季CBA联赛之青岛
日期:2016-03-17 20:36:13
9 [报告]
发表于 2013-04-16 06:24 |只看该作者
本帖最后由 rubyish 于 2013-04-16 04:39 编辑

看看:
  1. #!/usr/bin/perl
  2. # abc.pl
  3. my %h;
  4. while (<>) {
  5.     my ( @a, %g ) = split;
  6.     @g{@a} = (undef) x @a;
  7.     for (@a) {
  8.         next if !$h{$_} or $g{$_};
  9.         map $g{$_}++, keys %{ $h{$_} };
  10.     }
  11.     my @k = keys %g;
  12.     my $t = { map { $_, 1 } @k };
  13.     @h{@k} = ($t) x @k;
  14. }
  15. while ( my ( undef, $v ) = each %h ) {
  16.     my @v = keys $v;
  17.     print "@v$/";
  18.     delete @h{@v};
  19. }
复制代码
  1. perl abc.pl test.txt
复制代码

论坛徽章:
23
15-16赛季CBA联赛之吉林
日期:2017-12-21 16:39:27白羊座
日期:2014-10-27 11:14:37申猴
日期:2014-10-23 08:36:23金牛座
日期:2014-09-30 08:26:49午马
日期:2014-09-29 09:40:16射手座
日期:2014-11-25 08:56:112015年辞旧岁徽章
日期:2015-03-03 16:54:152015年迎新春徽章
日期:2015-03-04 09:49:0315-16赛季CBA联赛之山东
日期:2017-12-21 16:39:1915-16赛季CBA联赛之广东
日期:2016-01-19 13:33:372015亚冠之山东鲁能
日期:2015-10-13 09:39:062015亚冠之西悉尼流浪者
日期:2015-09-21 08:27:57
10 [报告]
发表于 2013-04-16 08:55 |只看该作者
本帖最后由 ly5066113 于 2013-04-16 09:06 编辑

回复 5# debateshang


行与行之间的冗余项很多,原来的代码有点小问题,改成这样虽然可以得到正确的结果,但速度确实很慢很慢。
  1. sed -n '
  2. s/.*/ & /
  3. H
  4. ${
  5.         g
  6.         :a
  7.         :b
  8.         s/ \([0-9]\{1,\}\) \([0-9 ]*\)\1 / \1 \2/
  9.         tb
  10.         s/\n\([0-9 ]*\)\( [0-9]\{1,\} \)\([0-9 ]*\)\(\n\)\(.*\)\2/\4\5\1\2\3/
  11.         ta
  12.         s/^\n//p
  13. }' file
复制代码
用下面的awk试试,我这里3分钟可以跑出来。
  1. awk '{m=NR;for(i=1;i<=NF;i++)if($i in a)m=m<a[$i]?m:a[$i];for(i=1;i<=NF;i++){k=a[$i];for(j in a)if(a[j]==k)a[j]=m}}END{for(i in a)b[a[i]]++;for(i in b){for(j in a)if(a[j]==i)printf j" ";print ""}}' file
复制代码
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP