カスタムユーティリティを使用した検索と置換

カスタムユーティリティを使用した検索と置換

正規表現に一致する値を変更するユーティリティを実行したいと思います。つまり、正規表現の各一致に対して一致を構成する文字を使用してユーティリティが呼び出されます。ユーティリティの出力は元の文字を置き換えます。

説明には以下を使用してくださいfactor

$ factor 230
230: 2 5 23

したがって、このユーティリティを使用して整数を選択し、その整数factorとして呼び出し、元の整数をfactor

サンプル入力で予想される内容は次のとおりです。

$ [code] <<< "Given the numbers with factors: 27, 13, 230, and 19, it is evident which are primes."
Given the numbers with factors: 27: 3 3 3, 13: 13, 230: 2 5 23, and 19: 19, it is evident which are primes.

これはうまくいくと思いましたが、入力を直接解釈したいようです。使用sed (GNU sed) 4.2.2

$ sed -E 's/([0-9]+)/factor \1/ge' <<< 'Given the numbers with factors: 27, 13, 230, and 19, it is evident which are primes.'
sh: 1: Given: not found

明らかに、私はこのフラグが何をしているのかわかりませんe。削除は、e正規表現が整数を正しく抽出することによって\1

私はこれを試してみますawk

$ awk '{r = gensub(/([0-9]+)/, system("factor \\1"), "g"); print r}' <<< 'Given the numbers with factors: 27, 13, 230, and 19, it is evident which are primes.'
1:
Given the numbers with factors: 0, 0, 0, and 0, it is evident which are primes.

1:それがどこから来たのかはわかりませんが、明らかにsystem。コマンドから標準出力をキャプチャする方法はないようですawk

私が求めているのは、コアユーティリティを使用できることです。

答え1

次のコマンドを実行します。

 perl -pe 's/(\d+)/qx(factor $1) =~ s|\n||r/ge'  input-file.txt

sedコマンドが機能しない理由は、Perlとは異なり、sedがパターン領域全体を実行するためです。 Perlは思うように実行し、s / /コマンドのrhsのように何度も実行し、あまりにも多くの部分を置き換えます。コマンド出力用。

これがsedが「Given:」を盗用したことを発見した場合、ユーティリティが見つからない理由です。与えられたのはパターン空間の始まりです。ファタイ

答え2

Perlでは可能です。使用分ける地図スカラーLCキャンセルUC優先参加する。コンマと状況感度が一致するため、最初に考えたよりも少し複雑です。

#!/usr/bin/perl
use warnings;
use strict;

sub rev {
    my ($string) = @_;
    my @words = split /(\W+)/, $string;
    my @caps = map scalar(/^[[:upper:]]/), @words;
    $_ = /\w/ ? lc reverse : $_ for @words;
    shift @caps and $_ = ucfirst for @words;
    return join "", @words
}

use Test::More tests => 1;
my $r = rev('Hello, my name is Yimin Rong.');
is $r, 'Olleh, ym eman si Nimiy Gnor.';

答え3

次のawkソリューションを試してください。

echo "Hello" | awk '{ for ( i=length($0);i>0;i-- ) { if (i == length($0) ) { printf "%s",toupper(substr($0,i,1)) } else {  printf "%s",tolower(substr($0,i,1)) } } printf "\n" }'

最後の文字から始めて、単語文字の各文字を文字ごとに取得します。最後の文字の場合は大文字に変換して印刷し、それ以外の場合は小文字で印刷します。

答え4

次のコマンドを実行します。

perl -pe 's/(\d+)/qx(factor $1) =~ s|\n||r/ge'  input-file.txt

関連情報