2012-05-31 2 views
10

Я смотрел код perl онлайн и наткнулся на то, что раньше не видел, и не могу узнать, что он делает (если есть).Двойные фигурные скобки в perl

if($var) {{ 
    ... 
}} 

Кто-нибудь знает, что означают двойные фигурные фигурные скобки?

+5

Я не думаю, что они ничего не делают. Я думаю, что они эквивалентны добавлению другого блока кода в блок if. – gpojd

ответ

11

Это трюк, обычно используемый с do, см. chapter Statement Modifiers in perlsyn.

Возможно, автор хотел выскочить из блока с next или тому подобное.

+0

Это похоже на что делает код. Последнее ключевое слово используется в коде в блоке if. Благодаря! – Chris

4

В случае if, они, вероятно, эквивалентно одиночными скобками (но это зависит от того, что находится внутри блока, так и вне if, ср

perl -E ' say for map { if (1) {{ 1,2,3,4 }} } 1 .. 2' 

). Есть причины использовать двойные скобки, хотя, с next или do, см. perlsyn. Например, попробуйте выполнить это несколько раз:

perl -E 'if (1) {{ say $c++; redo if int rand 2 }}' 

И попытайтесь заменить двойные скобки на отдельные.

+0

это хороший пример. – ysth

0

Без большого количества кода трудно сказать, для чего они используются. Это может быть опечатка, или это может быть голый блок, см. chapter 10.4 The Naked Block Control Structure in Learning Perl.

Голый блок добавляет лексическую область к переменным внутри блока.

+0

Не первый набор брекетов после 'if' уже предоставляет эту область видимости? Почему гнездо? Я в значительной степени не осведомлен о perl, поэтому, возможно, это очевидно для людей, но не для меня! –

+2

@ChrisFarmer: потому что 'if (1) {{my $ x = 1; } {my $ x = 2; }} ' – choroba

+0

Добавив вторую область, вы можете переназначить' $ var' и использовать ее в голой блоке таким образом, чтобы она не была видна вне блока if. –

14

Существует два заявления. Оператор «if» и bare block. Голые блоки - это петли, которые выполняются ровно один раз.

say "a"; 
{ 
    say "b"; 
} 
say "c"; 

# Outputs a b c 

Но будучи петлями, они влияют на next, last и redo.

my $i = 0; 
say "a"; 
LOOP: { # Purely descriptive (and thus optional) label. 
    ++$i; 
    say "b"; 
    redo if $i == 1; 
    say "c"; 
    last if $i == 2; 
    say "d"; 
} 
say "e"; 

# Outputs a b b c e 

(next делает то же самое, как last, так как нет следующего элемента.)

Они, как правило, используются для создания лексическую область.

my $file; 
{ 
    local $/; 
    open(my $fh, '<', $qfn) or die; 
    $file = <$fh>; 
} 
# At this point, 
# - $fh is cleared, 
# - $fh is no longer visible, 
# - the file handle is closed, and 
# - $/ is restored. 

Непонятно, почему один из них использовался здесь.


В качестве альтернативы, это может быть также конструктор хэшей.

sub f { 
    ... 
    if (@errors) { 
     { status => 'error', errors => \@errors } 
    } else { 
     { status => 'ok' } 
    } 
} 

коротка для

sub f { 
    ... 
    if (@errors) { 
     return { status => 'error', errors => \@errors }; 
    } else { 
     return { status => 'ok' }; 
    } 
} 

Perl заглядывает в фигурные скобки, чтобы угадать, если это голый цикл или хэш-конструктор. Поскольку вы не указали содержимое фигурных скобок, мы не можем сказать.

+1

+1 для упоминания о возможности создания хэш-конструктора. – chepner

0

{{может использоваться, чтобы вырваться из "if block".У меня есть код, который содержит:

if ($entry =~ m{\nuid: ([^\s]+)}) {{ # double brace so "last" will break out of "if" 
    my $uid = $1; 
    last if exists $special_case{$uid}; 
    # .... 

}} 
# last breaks to here 
Смежные вопросы