perl 哈希 排序_在Perl中对数组和哈希元素进行排序

perl 哈希 排序

perl 哈希 排序_在Perl中对数组和哈希元素进行排序_第1张图片

In Perl we have sort function which sorts a list alphabetically by default. But there is not the end. We need to sort:

在Perl中,我们具有sort函数,该函数默认情况下按字母顺序对列表进行排序。 但是没有尽头。 我们需要排序:

an array numerically  or

数字数组或

case insensitive strings or

不区分大小写的字符串或

case sensitive strings

区分大小写的字符串

hash contents by keys or

通过键或哈希值

hash contents by values or

按值散列内容或

reverse of all above said points

上述所有观点的反面

How sorting  works in Perl

Perl中排序的工作方式

Sort subroutine has three syntax and last one is the most used syntax.

Sort子例程具有三种语法,最后一种是最常用的语法。

    sort SUBNAME LIST

排序SUBNAME LIST

    sort BLOCK LIST

排序块列表

    sort LIST

排序清单

In list context, it sorts the LIST and returns the sorted list value. In scalar context, the behavior of sort() is undefined.

在列表上下文中,它对LIST排序并返回排序后的列表值。 在标量上下文中,sort()的行为未定义。

If SUBNAME or BLOCK is omitted, sorts in standard string comparison order.

Standard string comparison means based on ASCII value of those characters. Like @arr = qw (Call all). In this case it will be sorted as Call all which was not expected. So to make it work properly we use case-insensitive sort.

标准字符串比较表示基于那些字符的ASCII值。 就像@arr = qw(全部调用)。 在这种情况下,它将被分类为“调用所有不期望的事件”。 因此,为了使其正常工作,我们使用不区分大小写的排序。

 If SUBNAME is specified, it gives the name of a subroutine that returns an integer less than, equal to, or greater than 0 , depending on how the elements of the list are to be ordered. (The <=> and cmp operators are extremely useful in such routines.)

如果指定了SUBNAME,它将给出一个子例程的名称,该子例程将返回一个小于,等于或大于0的整数,具体取决于列表元素的排序方式。 (<=>和cmp运算符在此类例程中非常有用。)

Note: The values to be compared are always passed by reference and should not be modified . $a and $b are global variable and should not be declared as lexical variables.

注意:要比较的值始终通过引用传递,不应修改。 $ a和$ b是全局变量,不应声明为词法变量。

sort() returns aliases into the original list like grep, map etc  which should be  usually avoided for better readability.

sort()将别名返回到原始列表中,例如grep,map等,通常应避免使用别名以提高可读性。

As sorting always does string sorting, so to do numeric sorting we need to use a special syntax which a sort {$a ó $b} LIST. We will see these conditions using Perl codes.

由于排序始终是字符串排序,因此要进行数字排序,我们需要使用特殊的语法,即{{aó$ b} LIST。 我们将使用Perl代码查看这些条件。

How reverse sorting works

反向排序如何工作

Syntax to use reverse sort is reverse LIST. It works on sorted LIST usually. But in scalar context, it concatenates the elements of LIST and returns a string value with all characters in the opposite order.

使用反向排序的语法是反向LIST。 它通常适用于排序的LIST。 但是在标量上下文中,它将串联LIST的元素,并返回一个字符串值,其中所有字符的顺序相反。

In scalar context if argument is not passed it will reverse the value of $_

在标量上下文中,如果未传递参数,它将反转$ _的值

Ex:  

例如:

$_ = "dlrow ,olleH";

$ _ =“ dlrow,olleH”;

print scalar reverse;  #in this case print reverse would not works because it expects a LIST  

打印标量反转; #在这种情况下,打印反向将不起作用,因为它需要一个LIST

How <=> and cmp work?

<=>和cmp如何工作?

These are actually binary equality operator. Binary operator usually gives (0 or 1) or (true or false)  but these gives three values based on the comparison result.

这些实际上是二进制相等运算符。 二进制运算符通常给出(0或1)或(true或false),但是它们根据比较结果给出三个值。

Binary  "<=>" returns -1, 0, or 1 depending on whether the left argument is numerically less than, equal to, or greater than the right argument.

二进制“ <=>”返回-1、0或1,具体取决于左自变量在数值上小于,等于还是大于右自变量。

Binary "cmp" returns -1, 0, or 1 depending on whether the left argument is stringwise less than, equal to, or greater than the right argument.

二进制“ cmp”返回-1、0或1,具体取决于左参数是按字符串方式小于,等于还是大于右参数。

Never mix string and numeric values in LIST else sorting result will be fearsome :-(

切勿在LIST中混合使用字符串和数字值,否则排序结果将很可怕:-(

Try this out:

试试看:

my @arr1 = qw(1 two 3 0 4  Two 5 six 7 8 9 ten); 
	my @arr2 = sort {$a cmp $b} @arr1; 
	print "\n@arr2\n"; 
 

Let go through the codes for different scenarios:

让我们看一下针对不同场景的代码:

Example 1: Sorting  an array of strings (case-sensitive and case-insensitive examples)

示例1:对字符串数组进行排序(区分大小写和不区分大小写的示例)

 
	#!/usr/bin/perl 
	    use strict; 
	    use warnings; 
 
	    my @strarr = qw(two Two six Six alien Coders Alien coderS); 
	    my @sorted = sort {$a cmp $b} @strarr; # same result as of sort @strarr 
	    my @sortedcase  = sort { uc $a cmp uc $b } @strarr; #case-insensitivie 
	    print "\n@sorted\n@sortedcase\n"; 

Output:

输出:

Alien Coders Six Two alien coderS six two

外星人编码器六二外星人编码器六二

alien Alien Coders coderS six Six two Two

外星人外星编码员编码器六六二二

Note: try to always use in-case sensitive for better string sorting results.

注意:尝试始终使用区分大小写的字符,以获得更好的字符串排序结果。

Example 2: Sorting an array of numbers

示例2:对数字数组进行排序

The Perl sort function sorts by strings instead of by numbers. If you do it in general way it would fetch unexpected result.

Perl排序功能按字符串而不是数字排序。 如果以一般方式执行此操作,则将获取意外结果。

 #!/usr/bin/perl 
	    use strict; 
	    use warnings; 
 
	    my @numbers = (23, 1, 22, 7, 109, 9, 65, 3, 01, 001); 
 
	    my @sorted_numbers = sort @numbers; 
	    print "@sorted_numbers\n"; 
 

The output you would see would be:

您将看到的输出为:

    001 01 1 109 22 23 3 65 7 9

001 01 1 109 22 23 3 65 7 9

To sort numerically, declare your own sort block and use the binary equality operator i.e. flying saucer operator <=>:

要进行数字排序,请声明自己的排序块并使用二进制相等运算符,即飞碟运算符<=>:

 #!/usr/bin/perl 
	    use strict; 
	    use warnings; 
 
	    my @numbers = (23, 1, 22, 7, 109, 9, 65, 3, 01, 001); 
 
	    my @sorted_numbers = sort {$a <=> $b} @numbers; 
	    print "@sorted_numbers\n"; 

The output would now be:

现在的输出为:

    1 01 001  3 7 9 22 23 65 109

1 01 001 3 7 9 22 23 65 109

Note that $a and $b do not need to be declared, even with use strict on, because they are special sorting variables.

注意$ a和$ b即使是严格使用也不需要声明,因为它们是特殊的排序变量。

Example 3: Sorting array backwards (for string and numbers)

示例3:向后排序数组(用于字符串和数字)

To sort backwards you need to declare your own sort block, and simply put $b before $a. or use reverse keyword after simple sort.

要向后排序,您需要声明自己的排序块,只需将$ b放在$ a之前。 或在简单排序后使用反向关键字。

For example, the standard sort is as follows:

例如,标准排序如下:

   #!/usr/bin/perl 
	    use strict; 
	    use warnings; 
 
	    my @strings = qw(Jassi Alien Coders); 
 
	    my @sorted_strings = sort @strings; 
	    print "@sorted_strings\n"; 
 

    Alien Coders Jassi

外星人编码员贾西

To do the same, but in reverse order:

要执行相同操作,但顺序相反:

 #!/usr/bin/perl 
	    use strict; 
	    use warnings; 
 
	    my @strings = qw(Jassi Alien Coders); 
 
	    my @sorted_strings = sort {$b cmp $a} @strings; # or reverse sort @strings 
	    print "@sorted_strings\n"; 

The output is:

输出为:

Jassi Coders Alien

Jassi Coders外星人

And for numbers:

对于数字:

 #!/usr/bin/perl 
	    use strict; 
	    use warnings; 
 
	    my @numbers = (23, 1, 22, 7, 109, 9, 65, 3); 
 
	    my @sorted_numbers = sort {$b <=> $a} @numbers; # or reverse sort {$aó $b} @numbers 
	    print "@sorted_numbers\n"; 
 

The output is:

输出为:

    109 65 23 22 9 7 3 1

109 65 23 22 9 7 3 1

This was all about sorting array elements alphabetically or numerically. Now we will see how sorting works on hash elements.

这全部是关于按字母顺序或数字顺序对数组元素进行排序。 现在,我们将了解如何对哈希元素进行排序。

Example 4: Sorting hashes by keys

示例4:按键对散列进行排序

You can use sort to order hashes. For example, if you had a hash as follows:

您可以使用sort排序哈希。 例如,如果您具有以下哈希值:

Suppose we want to display the members for each community sorted alphabetically or say by keys, then this code will do so:

假设我们要显示按字母顺序或按键排序的每个社区的成员,那么此代码将这样做:

#!/usr/bin/perl 
	    use strict; 
	    use warnings; 
 
	    my %members = ( 
	        C => 1, 
	        Java => 7, 
	        Perl => 12, 
	        Linux => 3, 
	        Hacking => 8, 
	    ); 
	foreach my $language (sort keys %members) { 
	        print $language . ": " . $members{$language} . "\n"; 
	    } 
 

Output:

输出:

    C: 1

C:1

    Hacking: 8

骇客:8

    Java: 7

Java:7

    Linux: 3

Linux:3

    Perl: 12

Perl:12

If you want to sort the same hash by the values (i.e. the users beside each programming language), you could do the following:

如果要按值对相同的哈希排序(即每种编程语言旁边的用户),则可以执行以下操作:

 #!/usr/bin/perl 
	    use strict; 
	    use warnings; 
 
	    my %members = ( 
	        C => 1, 
	        Java => 7, 
	        Perl => 12, 
	        Linux => 3, 
	        Hacking => 8, 
	    ); 
	    # Using <=> instead of cmp because of the numbers 
	    foreach my $language (sort {$members{$a} <=> $members{$b}} keys %members){ 
	                print $language . ": " . $members{$language} . "\n"; 
	} 
 

Output:

输出:

    C: 1

C:1

    Linux: 3

Linux:3

    Java: 7

Java:7

    Hacking: 8

骇客:8

    Perl: 12

Perl:12

Example: 5 Sorting complex data structures

示例:5排序复杂的数据结构

We can also use sort function to sort complex data structures. For example, suppose we have an array of hashes (anonymous hashes) like:

我们还可以使用sort函数对复杂的数据结构进行排序。 例如,假设我们有一个哈希数组(匿名哈希),例如:

 my @aliens = ( 
	        { name => 'Jassi', age => 28}, 
	        { name => 'Somnath', age => 27}, 
	        { name => 'Ritesh', age => 24}, 
	        { name => 'Santosh', age => 29}, 
	        { name => 'Ranjan', age => 26}, 
	        { name => 'Kaushik', age => 25}, 
	    ); 

And we wish to display the data about the people by name, in alphabetical order, we could do the following:

我们希望按字母顺序显示姓名数据,我们可以执行以下操作:

#!/usr/bin/perl 
	    use strict; 
	    use warnings; 
 
	    my @aliens = ( 
	        { name => 'Jassi', age => 28}, 
	        { name => 'Somnath', age => 27}, 
	        { name => 'Ritesh', age => 24}, 
	        { name => 'Santosh', age => 29}, 
	        { name => 'Ranjan', age => 26}, 
	        { name => 'Kaushik', age => 25}, 
	    ); 
 
	    foreach my $person (sort {$a->{name} cmp $b->{name}} @aliens) { 
	        print $person->{name} . " is " . $person->{age} . "\n"; 
	    } 
 

    Jassi is 28

贾西28岁

    Kaushik is 25

考施克(Kaushik)是25

    Ranjan is 26

Ranjan是26

    Ritesh is 24

里特什24岁

    Santosh is 29

桑托什是29岁

    Somnath is 27

睡眠是27

Sorting the same hash by age and using a subroutine (inline function)

按年龄排序相同的哈希,并使用子例程(内联函数)

Rather than writing the code inline, you can also pass in a subroutine name. The subroutine needs to return an integer less than, equal to, or greater than 0. Do not modify the $a and $b variables as they are passed in by reference, and modifying them will probably confuse your sorting.

除了直接内联编写代码外,您还可以传入子例程名称。 该子例程需要返回小于,等于或大于0的整数。不要修改$ a和$ b变量,因为它们是通过引用传递的,修改它们可能会使您的排序混乱。

#!/usr/bin/perl 
	    use strict; 
	    use warnings; 
 
	    my @aliens = ( 
	        { name => 'Jassi', age => 28}, 
	        { name => 'Somnath', age => 27}, 
	        { name => 'Ritesh', age => 24}, 
	        { name => 'Santosh', age => 29}, 
	        { name => 'Ranjan', age => 26}, 
	        { name => 'Kaushik', age => 25}, 
	    ); 
 
	    foreach my $person (sort agecomp @aliens) { 
	# it just replaced {$a->{age} <=> $b->{age}} by agecomp inline function 
	        print $person->{name} . " is " . $person->{age} . " years old\n"; 
	    } 
 
	    sub agecomp { 
	        $a->{age} <=> $b->{age}; 
	    } 
 

The output would be:

输出为:

    Ritesh is 24 years old

Ritesh是24岁

    Kaushik is 25 years old

Kaushik是25岁

    Ranjan is 26 years old

Ranjan是26岁

    Somnath is 27 years old

Somnath是27岁

    Jassi is 28 years old

Jassi是28岁

    Santosh is 29 years old

Santosh今年29岁

To find out more on sort function,  run the command on Linux box:

要了解有关排序功能的更多信息,请在Linux框中运行以下命令:

    perldoc -f sort

perldoc -f排序

I have published this topic at Alien Coders

我已经在《 外星人编码》上发表了这个话题

and Here is the link for original article:Sorting an array and hash elements in Perl

这是原始文章的链接: 在Perl中对数组和哈希元素进行排序

Note: I am the owner of this website  and author of the tutorial

注意:我是该网站的所有者,也是本教程的作者

翻译自: https://www.experts-exchange.com/articles/10390/Sorting-an-array-and-hash-elements-in-Perl.html

perl 哈希 排序

你可能感兴趣的:(perl 哈希 排序_在Perl中对数组和哈希元素进行排序)