代码之家  ›  专栏  ›  技术社区  ›  Alex F

perl read()函数和不是ref的缓冲区背后的魔力是什么?

  •  6
  • Alex F  · 技术社区  · 15 年前

    我不明白Perl read($buf)函数是如何修改$buf变量的内容的$buf不是一个引用,所以参数是通过copy(根据我的c/c++知识)给出的。那么$buf变量是如何在调用者中被修改的呢?

    # Example 1
    $buf=''; # It is a scalar, not a ref
    $bytes = $fh->read($buf);
    print $buf; # $buf was modified, what is the magic ?
    
    # Example 2
    sub read_it {
        my $buf = shift;
        return $fh->read($buf);
    }
    my $buf;
    $bytes = read_it($buf);
    print $buf; # As expected, this scope $buf was not modified
    
    2 回复  |  直到 11 年前
        1
  •  11
  •   pilcrow    15 年前

    不需要任何魔法——如果愿意的话,所有perl子例程都是通过别名调用的。引用 perlsub :

    对于实际的标量参数。特别是,如果元素$[0] 更新相应的参数(或发生错误) 如果不可更新)。

    sub increment {
      $_[0] += 1;
    }
    
    my $i = 0;
    increment($i);  # now $i == 1
    

    在你的“例子2”中 read_it 附属的 副本 第一个元素 @_ $buf ,然后通过调用 read() . 传入 $_[0]

    sub read_this {
      $fh->read($_[0]);  # will modify caller's variable
    }
    sub read_that {
      $fh->read(shift);  # so will this...
    }
    
        2
  •  0
  •   JSBÕ±Õ¸Õ£Õ¹    15 年前

    read() 是一个内置函数,所以可以做魔术。但是,通过声明 function prototype :

    sub myread(\$) { ... }
    

    论元声明 \$ 表示参数作为引用隐式传递。

    内置的唯一魔法 read 它甚至在间接调用或作为filehandle方法调用时也能工作,这对于常规函数不起作用。