1

修饰符在这里/c做了一些我不明白的事情。我想知道为什么下面的代码会打印“abc3333”?

#!/usr/bin/perl
$x = 'abcdefg';
$x =~ tr/abc/123/c;
print $x;
4

3 回答 3

3

/c使搜索列表得到补充;也就是说,搜索每个列出的字符。

假设您在 range 中只有字符,则\0-\xff

tr/abc/123/c

相当于:

tr/\0-\x60\x64-\xff/123/

并且替换列表的最后一个字符根据需要重复多次以匹配搜索列表中的字符数(不使用 /d 时)。

所以“\0”变成“1”,“\1”变成“2”,“a”、“b”或“c”不变,其他任何字符变成“3”。

用 /c 指定替换列表是相当不寻常的;通常 /c 仅用于计数:

tr/abc//c # returns number of non-abc characters; string is unchanged

或删除:

tr/0-9//cd # delete all non-digits
于 2013-03-24T16:22:54.933 回答
1

/c通常用于修改/d

tr/...//d;    # Delete every matching char.
tr/...//cd;   # Delete every char that doesn't match.

或用于计数。

tr/...//;    # Returns number of matching chars.
tr/...//c;   # Returns number of chars that don't match.

我无法用非空替换集为它提供一个有用的示例,但它很容易解释:它只是使用搜索集的补集。请记住abc是字符 0x61、0x62 和 0x63,

tr/abc/123/c;

因此等价于

tr/\x00-\x60\x64-\x{FFFFFFFFF}/123/;            # Perl with 32bit ints
  or
tr/\x00-\x60\x64-\x{FFFFFFFFFFFFFFFFFF}/123/;   # Perl with 64bit ints

请记住,替换集的最后一个字符用于搜索集中没有对应字符的字符,

  • "\x00"变成1
  • "\x01"变成2
  • 其他匹配的都变成3.

tr这种行为与所基于的命令行工具完全一致tr///。我不确定没有 . 怎么/c可能有用/d,但也许是因为tr命令行工具具有的额外功能tr///(例如字符类)。

于 2013-03-24T15:56:42.000 回答
0

/c修饰符影响列表中字符的补码。它主要与/d修饰符一起使用,删除除给定字符集之外的所有字符。

my $string = 'ABCdef123';
$string =~ tr/a-z//cd;
print $string;

输出

def
于 2013-03-24T15:45:38.440 回答