[regex] 원본을 유지하면서 문자열에서 Perl 대체를 어떻게 수행합니까?

Perl에서 정규 표현식을 사용하여 문자열을 바꾸고 원래 변수를 변경하지 않고 다른 변수에 값을 저장하는 좋은 방법은 무엇입니까?

나는 보통 문자열을 새 변수에 복사 한 다음 s///새 문자열을 대체 하는 정규식에 바인딩 하지만 더 좋은 방법이 있는지 궁금합니다.

$newstring = $oldstring;
$newstring =~ s/foo/bar/g;



답변

이것은 원본을 변경하지 않고 문자열의 수정 사본을 얻는 데 항상 사용한 관용구입니다.

(my $newstring = $oldstring) =~ s/foo/bar/g;

perl 5.14.0 이상에서는 새로운 /r 비파괴 대체 수정자를 사용할 수 있습니다 .

my $newstring = $oldstring =~ s/foo/bar/gr; 

참고 : 위의 솔루션도 작동하지 g않습니다. 또한 다른 수정 자와도 작동합니다.


답변

진술 :

(my $newstring = $oldstring) =~ s/foo/bar/g;

다음과 같습니다.

my $newstring = $oldstring;
$newstring =~ s/foo/bar/g;

또는 Perl 5.13.2에서 /r비파괴 대체를 수행하는 데 사용할 수 있습니다 .

use 5.013;
#...
my $newstring = $oldstring =~ s/foo/bar/gr;


답변

아래에서 다음 use strict과 같이 말합니다.

(my $new = $original) =~ s/foo/bar/;

대신에.


답변

한 줄짜리 솔루션은 좋은 코드보다 shibboleth로 더 유용합니다. 좋은 Perl 코더는 그것을 알고 이해하지만, 시작하는 두 줄의 copy-and-modify couplet보다 훨씬 덜 투명하고 읽기 쉽습니다.

다시 말해서, 이것을하는 좋은 방법은 이미 하고 있는 방법 입니다. 가독성에 대한 불필요한 결정은 승리가 아닙니다.


답변

다른 pre-5.14 솔루션 : http://www.perlmonks.org/?node_id=346719 (japhy의 게시물 참조)

그의 접근 방식은 map배열에서도 잘 작동하지만 map임시 배열을 생성 하려면 계단식 배열이 필요합니다 (그렇지 않으면 원본이 수정됩니다).

my @orig = ('this', 'this sucks', 'what is this?');
my @list = map { s/this/that/; $_ } map { $_ } @orig;
# @orig unmodified


답변

나는 foo와 bar가 .. 어쨌든 프로그래밍에서 비 설명 적 용어를 꿈꾸는 사람은 누구입니까?

my $oldstring = "replace donotreplace replace donotreplace replace donotreplace";

my $newstring = $oldstring;
$newstring =~ s/replace/newword/g; # inplace replacement

print $newstring;
%: newword donotreplace newword donotreplace newword donotreplace


답변

Perl을 쓰면 use strict;선언 할 때에도 한 줄 구문이 유효하지 않다는 것을 알 수 있습니다.

와:

my ($newstring = $oldstring) =~ s/foo/bar/;

당신은 얻는다 :

Can't declare scalar assignment in "my" at script.pl line 7, near ") =~"
Execution of script.pl aborted due to compilation errors.

대신에 한 줄 더 길게 사용했던 구문은 구문 적으로 올바른 방법입니다 use strict;. 나를 위해, 사용 use strict;은 이제 습관입니다. 자동으로합니다. 모두가해야합니다.

#!/usr/bin/env perl -wT

use strict;

my $oldstring = "foo one foo two foo three";
my $newstring = $oldstring;
$newstring =~ s/foo/bar/g;

print "$oldstring","\n";
print "$newstring","\n";