Cari Kasus yang Cocok Ganti

14

Ambil tiga input, serangkaian teks T,; serangkaian karakter untuk menggantikan F,; dan serangkaian karakter untuk menggantikannya dengan R,. Untuk setiap substring Tdengan karakter yang sama (tidak sensitif huruf) F, gantilah dengan karakter dalam R. Namun, simpan case yang sama dengan teks aslinya.

Jika ada lebih banyak karakter Rdari pada F, karakter tambahan harus sama dengan mereka R. Jika ada angka atau simbol di dalamnya F, maka karakter yang sesuai di dalamnya Rharus menyimpan case-nya R. Fbelum tentu muncul di T.

Anda dapat mengasumsikan semua teks akan berada dalam kisaran ASCII yang dapat dicetak.

Contohnya

"Text input", "text", "test" -> "Test input"

"tHiS Is a PiEcE oF tExT", "is", "abcde" -> "tHaBcde Abcde a PiEcE oF tExT"

"The birch canoe slid on the smooth planks", "o", " OH MY " -> "The birch can OH MY e slid  OH MY n the sm OH MY  OH MY th planks"

"The score was 10 to 5", "10", "tEn" -> "The score was tEn to 5"

"I wrote my code in Brain$#@!", "$#@!", "Friend" -> "I wrote my code in BrainFriend"

"This challenge was created by Andrew Piliser", "Andrew Piliser", "Martin Ender" -> "This challenge was created by Martin Ender"

// Has a match, but does not match case 
"John does not know", "John Doe", "Jane Doe" -> "Jane does not know"

// No match
"Glue the sheet to the dark blue background", "Glue the sheet to the dark-blue background", "foo" -> "Glue the sheet to the dark blue background"

// Only take full matches
"aaa", "aa", "b" -> "ba"

// Apply matching once across the string as a whole, do not iterate on replaced text
"aaaa", "aa", "a" -> "aa"

"TeXT input", "text", "test" -> "TeST input"

Tautan kotak pasir

Andrew
sumber
Meminta contoh dengan casing aneh:"TeXT input", "text", "test"
Engineer Toast
@ Engineer Contoh ditambahkan
Andrew
Tidak yakin mengapa saya merasa "The birch canoe slid on the smooth planks", "o", " OH MY "sangat lucu, tetapi saya menyukai contoh itu.
Magic Gurita Guci

Jawaban:

3

Retina , 116 byte

i`(.+)(?=.*¶\1(¶.*)$)|.*¶.*$
¶¶$2¶$1¶¶
{T`l`L`¶¶.(?=.*¶[A-Z])
T`L`l`¶¶.(?=.*¶[a-z])
}`¶¶¶(.)(.*¶).
$1¶¶¶$2
¶¶¶¶.*|¶

Cobalah online! Penjelasan:

i`(.+)(?=.*¶\1(¶.*)$)|.*¶.*$
¶¶$2¶$1¶¶

Pencarian ini Tdan setiap kali ada pertandingan yang case-sensitive terhadap lookahead untuk Fpertandingan dikelilingi dalam banyak baris baru dan lookahead untuk Rjuga dimasukkan.

{T`l`L`¶¶.(?=.*¶[A-Z])
T`L`l`¶¶.(?=.*¶[a-z])
}`¶¶¶(.)(.*¶).
$1¶¶¶$2

Setiap surat salinan Rdisesuaikan jika cocok dengan yang cocok, berikut ini dipindahkan dari wilayah kerja sehingga surat berikutnya dapat diproses, sampai salinan Ratau pertandingan kehabisan surat.

¶¶¶¶.*|¶

Jika salinan Rkehabisan surat, maka sisa pertandingan akan didahului oleh 4 baris baru, jadi hapuslah. Kalau tidak, apa pun yang tersisa akan menjadi sisa salinan Ryang perlu disatukan dengan bagian input yang tidak cocok untuk menghasilkan hasilnya.

Neil
sumber
3

APL (Dyalog) , 75 73 72 byte

Anjuran untuk T,, Rdan Fdalam urutan itu. Rharus b diberikan dalam format transformasi Dyalog dan Fharus diberikan dalam format PCRE.

⍞⎕R(⍞∘{(⊣⌿d)l¨⍨(1∘⌷≠(⊢⌿d∊⎕A,lA)∧≠⌿)d≠(l819⌶)d←↑⍺⍵.Match↑¨⍨≢⍺})⍠1⊢⍞

Cobalah online!

 meminta T

 hasilkan itu (pisahkan 1 dan T )

⍞⎕R(... )⍠1 cepat Fdan R eplace cocok dengan hasil dari fungsi berikut:

⍞∘{…} mendapatkan fungsi monadik dengan mengikat diminta-untuk R sebagai argumen kiri ke:

  ≢⍺ hitung jumlah huruf dalam R

  ⍺⍵.Match↑¨⍨ ambil banyak surat dari masing-masing Rdan korek api
   adalah argumen kiri, yang kami ikat Rsebagai.
   adalah namespace di mana Matchberisi string yang saat ini ditemukan.

   mencampur keduanya menjadi matriks dua baris

  d← simpan sebagai d

  (...)   terapkan fungsi tersembunyi berikut untuk itu:

   819⌶ huruf kecil (mnemonik: 819 tampak seperti Besar )

   l← menyimpan fungsi itu sebagai l

  d≠ Boolean dimana d berbeda (yaitu memberi 0/1 untuk setiap huruf kecil / huruf besar)

  (... ) terapkan fungsi tersembunyi berikut untuk itu:

   ≠⌿ XOR vertikal

   ()∧ Boolean DAN dengan larik berikut:

    l⎕A lowercased A lphabet

    ⎕A, huruf kapital prependen A lphabet

    d∊ Boolean untuk setiap huruf dalam d apakah anggota itu (yaitu apakah surat)

    ⊢⌿ baris terakhir yaitu untuk karakter pertandingan apakah itu huruf

   1∘⌷≠ XOR dengan baris pertama, yaitu apakah setiap karakter Rhuruf besar

  (... )l¨⍨ gunakan itu untuk huruf kecil (jika 0) atau huruf besar (jika 1) setiap huruf dari:

   ⊣⌿ baris pertama, yaitu R


* Hitungan Byte untuk Dyalog Classic menggunakan ⎕OPT bukan .

Adm
sumber
2

Perl 5 , 108 byte

107 byte kode +1 untuk -p.

chomp(($s,$r)=<>);s|\Q$s|$&=~s!.!$_=substr$r,"@-",1;$&=~/[a-z]/i?$&eq uc$&?uc:lc:$_!egr.substr$r,"@-"+1|gie

Cobalah online!

Dom Hastings
sumber
2

Ditarik. Jawaban Dom mengalahkannya dengan tembakan panjang.

# Perl 5 , 136 + 1 (-p) = 137 byte

$f=<>;chomp$f;@R=($r=<>)=~/./g;for$i(/\Q$f/gi){$c=$n='';$"=$R[$c++],$n.=/[A-Z]/?uc$":/[a-z]/?lc$":$"for$i=~/./g;s/\Q$i/$n.substr$r,$c/e}

Cobalah online!

membuat luka besar setelah @ Hastings Hastings disebutkan \Q

# Perl 5 , 176 +1 (-p) = 177 byte

sub h($){chomp@_;pop=~s/[^a-z0-9 ]/\\$&/gir}$f=h<>;@R=($r=<>)=~/./g;for$i(/$f/gi){$c=$n='';$"=$R[$c++],$n.=/[A-Z]/?uc$":/[a-z]/?lc$":$"for$i=~/./g;$i=h$i;s/$i/$n.substr$r,$c/e}

Cobalah online!

Xcali
sumber
Lewati semua kotak uji sekarang;) 108: Coba online!
Dom Hastings
Anda harus mempostingnya. Mengalahkan milikku sedikit.
Xcali
Cukup adil! Sangat menyenangkan membuatnya. Saya menikmati tantangannya!
Dom Hastings
2

PowerShell , 190 byte

param($T,$F,$R)[regex]::Replace($T,'(?i)'+[regex]::escape($F),{param($m)-join(0..$R.Length|%{(($y=$R[$_]),("$y"."To$((('Low','Upp')[($z="$m"[$_])-cmatch($C='[A-Z]')]))er"()))[$z-match$C]})})

Cobalah online!

Penjelasan:

[Regex]::Replace( 
    input text T,
    Find text F with case insensitive and [regex]::escape() for symbols,
    {scriptblock} for computing the replacement
)

Blokir script replacment tidak:

$m is the matched text with case information
loop over each character in R as $y
    $z is the same index character in $m ($null if R overruns)
    $z-match'[A-Z]' checks if alphabetic, so we must to case-match
      otherwise, non-alphabetic or null, no case-match, return $y unchanged.
    if case-matching, check if z case-sensitive matches '[A-Z]' and
      use dynamic method calling from a generated string, either 
      $y."ToLower"()
      $y."ToUpper"()
      to force the match
-join the loop output into a replacement string

Kasus uji:

function f {
param($T,$F,$R)[regex]::Replace($T,'(?i)'+[regex]::escape($F),{param($m)-join(0..$R.Length|%{(($y=$R[$_]),("$y"."To$((('Low','Upp')[($z="$m"[$_])-cmatch($C='[A-Z]')]))er"()))[$z-match$C]})})
}

Import-Module Pester

$Cases = @(
    @{Text = "Text input"; Find = "text"; Replace = "test"; Result = "Test input" }
    @{Text = "tHiS Is a PiEcE oF tExT"; Find = "is"; Replace = "abcde"; Result = "tHaBcde Abcde a PiEcE oF tExT" }
    @{Text = "The birch canoe slid on the smooth planks"; Find = "o"; Replace = " OH MY "; Result = "The birch can OH MY e slid  OH MY n the sm OH MY  OH MY th planks" }
    @{Text = "The score was 10 to 5"; Find = "10"; Replace = "tEn"; Result = "The score was tEn to 5" }
    @{Text = "I wrote my code in Brain$#@!"; Find = "$#@!"; Replace = "Friend"; Result = "I wrote my code in BrainFriend" }
    @{Text = "This challenge was created by Andrew Piliser"; Find = "Andrew Piliser"; Replace = "Martin Ender"; Result = "This challenge was created by Martin Ender" }
    @{Text = "John does not know"; Find = "John Doe"; Replace = "Jane Doe" ; Result ="Jane does not know" }
    @{Text = "Glue the sheet to the dark blue background"; Find = "Glue the sheet to the dark-blue background"; Replace = "foo"; Result ="Glue the sheet to the dark blue background" }
    @{Text = "aaa" ; Find = "aa"; Replace = "b"; Result ="ba" }
    @{Text = "aaaa"; Find = "aa"; Replace = "a"; Result ="aa" }
    @{Text = "TeXT input"; Find = "text"; Replace = "test"; Result ="TeST input" }
)

Describe "Tests" {

    It "works on /<Text>/<Find>/<Replace>/ == '<Result>'" -TestCases $Cases {
        param($Text, $Find, $Replace, $Result)
        f $Text $Find $Replace | Should -BeExactly $Result
    }

}
TessellatingHeckler
sumber
1

TXR Lisp, 285 byte

(defun f(s f r)(let*((w(copy s))(x(regex-compile ^(compound,(upcase-str f))))(m(reverse(tok-where(upcase-str s)x))))(each((n m))(set[w n]r) (for((i(from n)))((< i (min(to n)(len w))))((inc i))(cond((chr-isupper[s i])(upd[w i]chr-toupper))((chr-islower[s i])(upd[w i]chr-tolower)))))w))

Asli yang diformat secara konvensional:

(defun f (s f r)
  (let* ((w (copy s))
         (x (regex-compile ^(compound ,(upcase-str f))))
         (m (reverse (tok-where (upcase-str s) x))))
    (each ((n m))
      (set [w n] r)
      (for ((i (from n))) ((< i (min (to n) (len w)))) ((inc i))
        (cond ((chr-isupper [s i]) (upd [w i] chr-toupper))
              ((chr-islower [s i]) (upd [w i] chr-tolower)))))
    w))
Kaz
sumber
1

JavaScript, 177 byte

(T,F,R)=>T.replace(eval(`/${F.replace(/[-\/\\^$*+?.()|[\]{}]/g,'\\$&')}/gi`),F=>[...R].map((r,i)=>/[A-Z]/i.test(f=F[i]||'')?r[`to${f>'`'&&f<'{'?'Low':'Upp'}erCase`]():r).join``)

Kurang golf:

(T,F,R) => T.replace(
    eval(`/${F.replace(/[-\/\\^$*+?.()|[\]{}]/g,'\\$&')}/gi`),
    F=>[...R].map((r,i) =>
        /[A-Z]/i.test(f = F[i] || '')
            ? r[`to${
                f > '`' && f < '{'
                    ? 'Low'
                    : 'Upp'
                }erCase`]()
            : r
    ).join``
)

47 byte berasal dari fungsi pelarian regex ini karena program harus menangani simbol. :(

Darrylyeo
sumber
1

Python 2 , 193 200 byte

T,F,R=input()
w=str.lower
i=-len(T)
l=len(F)
T+=' '
while i:
 s=T[i:i+l]
 if w(s)==w(F):T=T[:i]+`[[y,[w(y),y.upper()][x<'a']][x.isalpha()]for x,y in zip(s,R)]`[2::5]+R[l:]+T[i+l:];i+=l-1
 i+=1
print T

Cobalah online!

tongkat
sumber
Ini (193 byte, dari tautan TIO) akan gagal menemukan kecocokan di akhir string.
tehtmi
1

Python 3 , 183 byte

import re
j="".join
f=lambda T,F,R:j((p,j((y,(y.lower(),y.upper())[x<'a'])[x.isalpha()]for(x,y)in zip(p,R))+R[len(F):])[i%2>0]for i,p in enumerate(re.split('('+re.escape(F)+')',T,0,2)))

Cobalah online!

re.split + menjaga semua elemen genap dan mengganti semua elemen aneh dengan transformasi yang benar dari string pengganti:

>>> re.split("(is)","tHiS Is a PiEcE oF tExT",0,2) # 2=re.IGNORE_CASE
['tH', 'iS', ' ', 'Is', ' a PiEcE oF tExT']
jferard
sumber
1

C (gcc) , 210 211 207 189 byte

Harus menambahkan satu byte untuk memperbaiki bug dengan kapitalisasi untuk testcase "BrainFriend"

Wow, ini membosankan ... Sekarang untuk bermain golf beberapa byte

char*c,*p;d,l;f(t,f,r){for(d=isalpha(*(p=f)),p=c=t;c=strcasestr(c,f);p=c+=l>0?l:0){for(l=strlen(f);p<c;)putchar(*p++);for(p=r;*p;p++,c+=l-->0)putchar(d*l<1?*p:*c&32?*p|32:*p&~32);}puts(p);}

Cobalah online!

Cleblanc
sumber
Saya mungkin kehilangan sesuatu yang jelas, tetapi mengapa Anda perlu *(p=f)ketika Anda mengatur p=c=tsetelahnya? Saya mencobanya dengan adil *fdan tidak berhasil, jadi tidak segera ditimpa.
Andrew
f adalah dengan cacat int sehingga kita tidak bisa dereference untuk mendapatkan char, tetapi p adalah char *
cleblanc
Ah, itu masuk akal. Jadi ini cara menulis yang lebih pendek *((char*)f)? Keren!
Andrew
1

C # (Mono C # compiler) , 241 byte

using System.Text.RegularExpressions;
class Program {
static void Main(string[] args) {
r("Text input","text","Test");
}
static void r(string v,string i,string u)
{
System.Console.WriteLine(Regex.Replace(v,i,u,RegexOptions.IgnoreCase)); 
}
}

Cobalah online!

rivalC
sumber
1
Selamat datang di PPCG! Anda dapat menghapus sedikit spasi di sini, dan sebenarnya Anda perlu mengambil input sebagai argumen atau input (mengkodekannya dilarang) atau Anda sebenarnya bisa saja memasukkan fungsi; Anda bahkan tidak memerlukan Action<string,string,string> r =bagian
HyperNeutrino