免费注册 查看新帖 |

Chinaunix

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

[文本处理] 一个类似容器的问题 [复制链接]

论坛徽章:
7
亥猪
日期:2013-10-10 17:00:29辰龙
日期:2013-10-12 16:23:19卯兔
日期:2013-11-18 17:01:27金牛座
日期:2014-09-09 10:17:052015七夕节徽章
日期:2015-08-21 11:06:172015亚冠之柏太阳神
日期:2015-09-25 13:56:42数据库技术版块每日发帖之星
日期:2016-08-06 06:20:00
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2014-07-24 14:04 |只看该作者 |倒序浏览
本帖最后由 li0924 于 2014-07-24 17:04 编辑

输入文件如下 a b
  1. $ cat a
  2. s1      x       1000
  3. s2      x       500
  4. s7      x       400
  5. s3      y       500
  6. s8      y       500
  7. s4      z       1000
  8. $ cat b
  9. x       M1      140
  10. x       M1      160
  11. x       M2      300
  12. x       M3      600
  13. x       M7      700
  14. y       M4      500
  15. y       M5      500
  16. z       M6      1000
复制代码
想要的结果為 b中 第一列 对应a中的 第二列 ,b的累加数量满足 a 表中数量,当满足时,则将多余数量拆分a表对应的下一笔第一列,全部分配完成
不考虑b数量超出。备注同一个x,y,z在a,b中数量是相等的;
输出的结果如下(数量拆分如红色和蓝色部分):
s1        x        M1        140
s1        x        M1        160
s1        x        M2        300
s1        x        M3        400
s2        x        M3        200

s2        x        M7        300
s7        x        M7        400

s3        y        M4        500
s8        y        M5        500
s4        z        M6        1000
我的答案
游客,如果您要查看本帖隐藏内容请回复

论坛徽章:
60
20周年集字徽章-20	
日期:2020-10-28 14:04:3015-16赛季CBA联赛之北京
日期:2016-07-06 15:42:0715-16赛季CBA联赛之同曦
日期:2016-06-12 10:38:0915-16赛季CBA联赛之佛山
日期:2016-05-27 11:54:56黄金圣斗士
日期:2015-12-02 11:44:35白银圣斗士
日期:2015-11-25 14:32:43白银圣斗士
日期:2015-11-23 12:53:352015亚冠之布里斯班狮吼
日期:2015-10-21 16:55:482015亚冠之首尔
日期:2015-09-01 16:46:052015亚冠之德黑兰石油
日期:2015-08-31 11:39:192015亚冠之萨济拖拉机
日期:2015-08-28 21:06:5315-16赛季CBA联赛之广东
日期:2016-07-12 14:58:53
2 [报告]
发表于 2014-07-24 14:28 |只看该作者
看了半天,没看明白

论坛徽章:
7
亥猪
日期:2013-10-10 17:00:29辰龙
日期:2013-10-12 16:23:19卯兔
日期:2013-11-18 17:01:27金牛座
日期:2014-09-09 10:17:052015七夕节徽章
日期:2015-08-21 11:06:172015亚冠之柏太阳神
日期:2015-09-25 13:56:42数据库技术版块每日发帖之星
日期:2016-08-06 06:20:00
3 [报告]
发表于 2014-07-24 14:30 |只看该作者
回复 2# reyleon
例如文件b中第4行变成红色部分;第5行变成蓝色部分


   

论坛徽章:
60
20周年集字徽章-20	
日期:2020-10-28 14:04:3015-16赛季CBA联赛之北京
日期:2016-07-06 15:42:0715-16赛季CBA联赛之同曦
日期:2016-06-12 10:38:0915-16赛季CBA联赛之佛山
日期:2016-05-27 11:54:56黄金圣斗士
日期:2015-12-02 11:44:35白银圣斗士
日期:2015-11-25 14:32:43白银圣斗士
日期:2015-11-23 12:53:352015亚冠之布里斯班狮吼
日期:2015-10-21 16:55:482015亚冠之首尔
日期:2015-09-01 16:46:052015亚冠之德黑兰石油
日期:2015-08-31 11:39:192015亚冠之萨济拖拉机
日期:2015-08-28 21:06:5315-16赛季CBA联赛之广东
日期:2016-07-12 14:58:53
4 [报告]
发表于 2014-07-24 14:34 |只看该作者
回复 3# li0924


   
就是这个,咋变来的,没整明白呀... 你的主题好多错别字. 语句也不容易看懂

论坛徽章:
7
亥猪
日期:2013-10-10 17:00:29辰龙
日期:2013-10-12 16:23:19卯兔
日期:2013-11-18 17:01:27金牛座
日期:2014-09-09 10:17:052015七夕节徽章
日期:2015-08-21 11:06:172015亚冠之柏太阳神
日期:2015-09-25 13:56:42数据库技术版块每日发帖之星
日期:2016-08-06 06:20:00
5 [报告]
发表于 2014-07-24 14:46 |只看该作者
回复 4# reyleon

如a中一行数据对应一个容器;容量是第3列的值;
a中第一行是说明该容器的容量是1000”;第二列为x跟b中第列对应;b中第3列的值是140;少于1000.说明没超过这个容器;该容器还没满;还是1000-140=860
就拿b第二行来比对;160也少于860;直到b的第4行;s1的容器还剩400(1000-140-160-300);而b的第3列是600>400;剩余的200要倒入s2容器里面;也就是a中的第二行;后面依次类推。


   

论坛徽章:
60
20周年集字徽章-20	
日期:2020-10-28 14:04:3015-16赛季CBA联赛之北京
日期:2016-07-06 15:42:0715-16赛季CBA联赛之同曦
日期:2016-06-12 10:38:0915-16赛季CBA联赛之佛山
日期:2016-05-27 11:54:56黄金圣斗士
日期:2015-12-02 11:44:35白银圣斗士
日期:2015-11-25 14:32:43白银圣斗士
日期:2015-11-23 12:53:352015亚冠之布里斯班狮吼
日期:2015-10-21 16:55:482015亚冠之首尔
日期:2015-09-01 16:46:052015亚冠之德黑兰石油
日期:2015-08-31 11:39:192015亚冠之萨济拖拉机
日期:2015-08-28 21:06:5315-16赛季CBA联赛之广东
日期:2016-07-12 14:58:53
6 [报告]
发表于 2014-07-24 14:47 |只看该作者
好像看懂了..

论坛徽章:
32
处女座
日期:2013-11-20 23:41:20双子座
日期:2014-06-11 17:20:43戌狗
日期:2014-06-16 11:05:00处女座
日期:2014-07-22 17:30:47狮子座
日期:2014-07-28 15:38:17金牛座
日期:2014-08-05 16:34:01亥猪
日期:2014-08-18 13:34:25白羊座
日期:2014-09-02 15:03:55金牛座
日期:2014-11-10 10:23:58处女座
日期:2014-12-02 09:17:52程序设计版块每日发帖之星
日期:2015-06-16 22:20:002015亚冠之塔什干火车头
日期:2015-06-20 23:28:22
7 [报告]
发表于 2014-07-24 14:52 |只看该作者
本帖最后由 yestreenstars 于 2014-07-24 16:27 编辑
  1. [root@localhost ~]# awk -vOFS='\t' 'NR==FNR{a[$2]++;b[$2,a[$2]]=$1;c[$2,a[$2]]=$3;next}{if(!d[$1]++)n=1;if(!c[$1,n])n++;$0=b[$1,n]"\t"$0;while(c[$2,n]<$4){t=$4-c[$2,n];$1=b[$2,n];$4=c[$2,n];print;$4=t;n++};$1=b[$2,n];c[$2,n]-=$4}1' a b
  2. s1        x        M1        140
  3. s1        x        M1        160
  4. s1        x        M2        300
  5. s1        x        M3        400
  6. s2        x        M3        200
  7. s2        x        M7        300
  8. s7        x        M7        400
  9. s3        y        M4        500
  10. s8        y        M5        500
  11. s4        z        M6        1000
  12. [root@localhost ~]#
复制代码

论坛徽章:
7
亥猪
日期:2013-10-10 17:00:29辰龙
日期:2013-10-12 16:23:19卯兔
日期:2013-11-18 17:01:27金牛座
日期:2014-09-09 10:17:052015七夕节徽章
日期:2015-08-21 11:06:172015亚冠之柏太阳神
日期:2015-09-25 13:56:42数据库技术版块每日发帖之星
日期:2016-08-06 06:20:00
8 [报告]
发表于 2014-07-24 14:53 |只看该作者
本帖最后由 li0924 于 2014-07-24 14:55 编辑

回复 7# yestreenstars
膜拜;
代码有点不对;容器号还没对应上

   

论坛徽章:
32
处女座
日期:2013-11-20 23:41:20双子座
日期:2014-06-11 17:20:43戌狗
日期:2014-06-16 11:05:00处女座
日期:2014-07-22 17:30:47狮子座
日期:2014-07-28 15:38:17金牛座
日期:2014-08-05 16:34:01亥猪
日期:2014-08-18 13:34:25白羊座
日期:2014-09-02 15:03:55金牛座
日期:2014-11-10 10:23:58处女座
日期:2014-12-02 09:17:52程序设计版块每日发帖之星
日期:2015-06-16 22:20:002015亚冠之塔什干火车头
日期:2015-06-20 23:28:22
9 [报告]
发表于 2014-07-24 16:18 |只看该作者
回复 8# li0924

噢,是的,这都被你发现了,待会再改,先用perl来一发~
  1. #!/usr/bin/perl
  2. open(FILE1, 'a') or die;
  3. open(FILE2, 'b') or die;

  4. my(%hash1, %hash2);

  5. while(<FILE1>){
  6.         @_ = split;
  7.         push(@{$hash1{$_[1]}}, $_[0]);
  8.         push(@{$hash2{$_[1]}}, $_[2]);
  9. }

  10. while(<FILE2>){
  11.         @_ = split;
  12.         lable:
  13.         my $temp = shift @{$hash2{$_[0]}};
  14.         next unless defined $temp;
  15.         if($temp > $_[2]){
  16.                 $temp -= $_[2];
  17.                 unshift(@{$hash2{$_[0]}}, $temp);
  18.         }else{
  19.                 print join("\t", $hash1{$_[0]}[0], @_[0,-2], $temp), $/;
  20.                 $_[2] -= $temp;
  21.                 shift @{$hash1{$_[0]}};
  22.                 next unless $_[2];
  23.                 goto lable;
  24.         }
  25.         print join("\t", $hash1{$_[0]}[0], @_), $/;
  26. }

  27. close(FILE1);
  28. close(FILE2);
复制代码

论坛徽章:
1
CU十二周年纪念徽章
日期:2013-10-24 15:41:34
10 [报告]
发表于 2014-07-24 16:22 |只看该作者
好多大神出没...
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

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

清除 Cookies - ChinaUnix - Archiver - WAP - TOP