2014-09-30 10 views
10

Perl'in sort() işlevini kullanmak istediğim sonuçları nasıl alacağımı anlıyorum, bu daha çok sort() iç işleyişi hakkında bir soru.

"$ a" ve "$ b" değişkenleri nereden geliyor? Sıralama için belgeleri okudum ve belirsiz görünüyor. "$ A" ve "$ b" nelerdir ve onları özel yapan nedir?

örn:

my @sorted_list = sort {$a cmp $b} @unsorted_list; 

Nasıl sıralamanıza alamadım neden "$ için hata "Küresel sembol açık paket adı gerektiriyor" "$ a" ve "$ b" ve ne yapacağını biliyor mu bir "veya" $ b "?

+6

'perldoc strict' konumundan:' sort() tarafından özel kullanımlarından dolayı $ a ve $ b değişkenleri bu denetimden muaf tutulur. – toolic

+0

$ a ve $ b kırmızı kutularda öğelerdir. http://en.wikipedia.org/wiki/Merge_sort#mediaviewer/File:Merge-sort-example-300px.gif –

cevap

17

$a ve $b muaf genel değişkenlerdir; Perl'in, ilan edilmeksizin (her yerde) kullanılmasına izin vermesinden muaftırlar. Sıralama işlevi tarafından ayarlanır. Tasnif edilmemiş herhangi bir globalin (sıkı modda) kullanılması, bir hatayı tetikleyecektir.

Sıralama işlevi, atıfta bulunduğunuz form olan bir kod bloğu olan çeşitli girdi formlarını kabul eder.

{$a cmp $b}

o ayrıştırılır ve sıralama işlevi bir "kod yığın" olarak geçirilir, bir kod bloğudur, ve Perl tür argümanlarını kontrol eder ve bir kod bloğu alırsa, sıralama $a ve $b, eğer ayarlayacaktır kod bloğu içinde paket globals olarak bulunurlar ve her bir öğe çiftinin $a ve $b'a ayrılmasını sağlar. Tek yapmanız gereken sıralama algoritmasını kontrol etmek için onlara bakmaktır. Aksi takdirde, dahili algoritma kullanılır (bence sıralama birleşimidir).

http://perldoc.perl.org/functions/sort.html

$a ve $b onlar paket globaller (veya sadece globaller) vardır, lexicals değildir.

bir ana olarak yazabilirsiniz:

sort {$main::a cmp $main::b} @list; 

Veya başka pakette

, yazabilirsiniz: Aslında böyle bir ön ek olmamalıdır

package foo; 

sort {$foo::a cmp $foo::b} @list; 

; Şu anki paketinizde $a ve $b'un aslında globals olduğunu ve Perl'in sıkı bir modda bile tanımlamanıza izin vereceğini bilmesine rağmen, sıralama işlevinde bazı sihirli $a olmadığını gösteriyorum.

Herhangi bir değişken (katı modda) kullanamazsınız. Deneyin: Sen tür kapsamındaki bir sözcük (benim $ a) kullanamazsınız

sort {$A cmp $B} @list; 

Global symbol "$A" requires explicit package name at sort.pl 

.

my $a; 
sort {$a cmp $b} @list; 

Can't use "my $a" in sort comparison at sort.pl line 13. 

$a ve $b özeldir Perl yerde. Bunlar, sıralama ile ilgisiz olan sıkı moddan muaftırlar, ancak muafiyetin nedeni sort idi.

+0

Çok güzel bir cevap. Keşke iki kere daha yapabilirim. – LeoNerd

5

Perl'in “sort()” işlevinin [karşılaştırma kodu] içinde tam olarak "a $ a" ve "$ b" olan nedir?

Sıralama için değerler listesinden iki değer. Blok, son sonuçta diğerine nasıl konumlandırılacağı hakkında bilgi vermektir.

"$ a" ve "$ b" nelerdir ve bunları özel yapan nedir?

Paket değişkenleri ve bir hata olmalarını kullanmayı düşünün etmediğini use strict 'vars'; dışında onlar hakkında özel bir şey yok.

"$ a" ve "$ b" değişkenleri nereden geliyor? Bunlar, sort tarafından doldurulmuştur.

Nasıl çeşit "$ a" ve "$ b"

Onun işlevini gerçekleştirmek için gerektiği gibi bunları doldurmak dışında onlarla hiçbir şey yapmaz ne yapacağını biliyor.

Neden "$ a" veya "$ b" için "Global sembolün açık paket adı gerektiriyor" hatası almıyorsunuz?

Bu onları kullanmak oldukça zor olurdu! Bir yerel değişken, my $a veya my $b tanımlamak ve sonra denemek ve bu [sözcük] değişkenler görünür olduğu yere bir kapsamda sort kullanmak ne olur

? senin karşılaştırma işlevi my $a ve/veya my $b kapsamında ise

, bu paket değişkenlerin yerine bu değişkenleri kullanır sort doldurur.

Perl, yapılması kolay bir hata olabileceğini fark eder, bu yüzden kontrol eder.

$ perl -c -e'sort { my ($a,$b); $a cmp $b } @a;' 
Can't use "my $a" in sort comparison at -e line 1. 
+0

Yani ne diyorsunuz "$ a" ve "$ b" kullanımı özel olarak 'sort()' işlevi ve başka işlev yok? Yerel bir değişken, "a $ a" veya "$ b" değerlerini tanımlarsanız ve sonra bu yerel değişkenlerin göründüğü bir kapsam içinde sıralama kullanmayı denerseniz ne olur? – tjwrona1992

+1

@ tjwrona1992 bir adım atın ve ne olduğunu görün! –

+0

@ tjwrona1992 - Cevabımın alt kısmına bakın. Bir sözlük kullanamazsınız (ancak neden kendiniz denemiyorsunuz ve göremiyorsunuz?) – codenheim

2

Diğer cevaplar iyidir, bu yüzden tekrarlamamaya çalışıyorum, ancak sorunuzun bir kısmı gerçekten yanıtlanmadı.

"$ a" ve "$ b" değişkenleri nereden geliyor?

codenheim yazdığı gibi, sort temelde (Bu açık bir modül veya main modül olsun) sizin modüle kadar uzanan ve kapsamı değişkenleri belirlemedir. Nasıl? Sadece strict refs'u geçici olarak kapatarak ve tam nitelikli değişken adını yazarak. Bu işlemle, değişkene ${$variable_name} üzerinden erişilebilir.

my $pkgname = caller(); 
my $varname = "${pkgname}::a"; 
no strict 'refs'; 
${$varname} = value; 

Not: Ben List::Util için source bu tekniğin keşfetti.