- 论坛徽章:
- 0
|
回复 1# mpstat
题目很有意思,谢谢lz提供了这么有趣的题目~膜拜一下前面的awk大牛们~
我用的是perl。- #!/usr/bin/perl
- use warnings;
- use strict;
- open my $fi, '<', "name.txt";
- my ( %hash, $group, $nation, $coach, $caption );
- while ( <$fi> ) {
- chomp;
- if ( /^\s*$/ or /^\s*#/) {
- next;
- }
- if ( /^Group (\w)$/ ) {
- $group = $1;
- next;
- }
- if ( /^(\w+)$/ ) {
- $nation = $1;
- next;
- }
- if ( /^Head coach:\s+(.*) \((.*)\)$/ ) {
- $coach = { 'name' => $1, 'nation' => $2,};
- next;
- }
- if ( /^\s+\d+/ ) {
- if (/^\s+\d+ (\w{2}) (.+?) \(c\)\s+\((\d{4})-(\d{2})-(\d{2})\)\s+\(aged (\d+)\)\s+(.+)$/ ) {
- # posi name birth age club
- $caption = 1;
- }
- elsif (/^\s+\d+ (\w{2}) (.+?)\s+\((\d{4})-(\d{2})-(\d{2})\)\s+\(aged (\d+)\)\s+(.+)$/ ) {
- # posi name birth age club
- $caption = 0;
- }
- # some player with the same name, and set the key = $nation.'_'.$name
- $hash{$nation.'_'.$2} = { 'posi' => $1,
- 'birth' => $3.$4.$5,
- 'age' => $6,
- 'club' => $7,
- 'caption' => $caption,
- 'group' => $group,
- 'nation' => $nation,
- 'coach' => $coach->{'name'},
- };
- }
- }
- close $fi;
- # 1. Get the Youngest player
- my @names = map { (split /_/, $_)[1] } keys %hash;
- my @birth = map { $hash{$_}->{'birth'} } keys %hash;
- my @a = sort {$birth[$a]<=>$birth[$b]} 0..$#birth;
- print "\n1. The youngest player(s) is(are):\n";
- print "\t$names[$a[$_]]\t$birth[$a[$_]]\n" foreach &get_idx_with_same_value(\@a, \@birth, 'end');
- # 2. Get the Oldest player
- print "\n2. The oldest player(s) is(are):\n";
- print "\t$names[$a[$_]]\t$birth[$a[$_]]\n" foreach &get_idx_with_same_value(\@a, \@birth, 'head');
- # 3. Get the day on which most people are birth
- my %hash3;
- foreach ( @birth ) {
- /(\d\d)$/;
- $hash3{$1}++;
- }
- my @keys = keys %hash3;
- my @values = values %hash3;
- @a = sort {$values[$a]<=>$values[$b]} 0..$#values;
- print "\n3. The most birth day(s) is(are):\n";
- print "\t$keys[$a[$_]]\t$values[$a[$_]]\n" foreach &get_idx_with_same_value(\@a, \@values, 'end');
- # 4. Get the same birthday with me
- my @same_birth;
- foreach ( keys %hash ) {
- push @same_birth, $_ if $hash{$_}->{'birth'} == '19820501';
- }
- my $same_birth = join ', ', map { (split /_/, $_)[1] } @same_birth;
- if ( $same_birth ) {
- print "\n4. Player with the same birthday with me are(is):\n\t$same_birth\n";
- }
- else {
- print "\n4. No one has the same birthday with me.\n";
- }
- # 5. Get the nation and coach and group of one input name
- print "\n5. Please input one player name:\n";
- my $flag = 0;
- my $input = <STDIN>;
- chomp $input;
- foreach ( keys %hash ) {
- if ( $input eq (split /_/, $_)[1] ) {
- $flag = 1;
- print "$input:\n\tnation: ".$hash{$_}->{'nation'}."\n\tcoach: ".$hash{$_}->{'coach'}."\n\tgroup: ".$hash{$_}->{'group'}."\n"
- }
- }
- print "ERROR: non exist player: \"$input\"\n" if $flag == 0;
- # 6. Get the club with most people
- my %hash6;
- $hash6{$hash{$_}->{'club'}}++ for keys %hash;
- @keys = keys %hash6;
- @values = values %hash6;
- @a = sort {$values[$a]<=>$values[$b]} 0..$#values;
- print "\n6. The club(s) with most people is(are):\n";
- print "\t$keys[$a[$_]]\t$values[$a[$_]]\n" foreach &get_idx_with_same_value(\@a, \@values, 'end');
- # 7. Get the position that most caption play
- my %hash7;
- foreach ( keys %hash ) {
- $hash7{$hash{$_}->{'posi'}}++ if $hash{$_}->{'caption'};
- }
- @keys = keys %hash7;
- @values = values %hash7;
- @a = sort {$values[$a]<=>$values[$b]} 0..$#values;
- print "\n7. The position(s) with most caption is(are):\n";
- print "\t$keys[$a[$_]]\t$values[$a[$_]]\n" foreach &get_idx_with_same_value(\@a, \@values, 'end');
- # 8. Get the number of people older than me
- my $older_than_me = 0;
- foreach ( keys %hash ) {
- $older_than_me++ if $hash{$_}->{'birth'} < '19771029';
- }
- if ( $older_than_me ) {
- print "\n8. The number older than me is: $older_than_me\n";
- }
- else {
- print "\n8. No one is older than me!\n";
- }
- # 9. Get the day no one is birth
- my @first_9_day = qw(01 02 03 04 05 06 07 08 09);
- my @monthes = @first_9_day;
- push @monthes, qw(10 11 12);
- my @days = @first_9_day;
- push @days, 10..29;
- my $num;
- my @birth_days;
- for $num ( @monthes ) {
- push @birth_days, $num.$_ foreach @days;
- }
- push @birth_days, qw(0130 0131 0330 0331 0530 0531 0730 0731 0830 0831 1030 1031 1230 1231 0430 0630 0930 1130);
- my %hash9 = map { $_ => 1 } @birth_days;
- foreach ( keys %hash ) {
- my $player = $_;
- $hash{$player}->{'birth'} =~ /(\d\d\d\d)$/;
- $hash9{$1} = 0;
- }
- my @no_one_birth = sort { $a<=>$b } grep { $hash9{$_} } keys %hash9;
- if ( @no_one_birth ) {
- print "\n9. The day(s) no one is birth is(are):\n\t@no_one_birth\n"
- }
- else {
- print "\n9. Any day has a player birth\n";
- }
- # 10. Get the number of each position
- my %hash10;
- foreach ( keys %hash ) {
- my $posi = $hash{$_}->{'posi'};
- $hash10{$posi}++;
- }
- print "\n10. The numbers of each postion are:\n";
- print "\t$_: $hash10{$_}\n" for keys %hash10;
- # subroutine(s)
- sub get_idx_with_same_value {
- my ( $r_idx, $r_array, $locate ) = @_;
- my @array;
- if ( $locate eq 'head' ) {
- my $cnt = 0;
- my $mark = $r_array->[$cnt];
- while ( $mark == $r_array->[$cnt] ) {
- push @array, $cnt;
- $cnt++;
- }
- }
- elsif ( $locate eq 'end' ) {
- my $cnt = @$r_idx - 1;
- my $mark = $r_array->[$cnt];
- while ( $mark == $r_array->[$cnt] ) {
- push @array, $cnt;
- $cnt--;
- }
- }
- else {
- die "ERROR!!!\n";
- }
- return @array;
- }
复制代码 子函数get_idx_with_same_value是考虑可能有并列的情况而设计的。
perl是在windows下的cmd里运行出来的,最近才开始用windosw下的perl的,输出结果不知道怎么copy,尴尬。 |
|