ANNNOUNNNCCCEEERRR 음성


18

문자와 공백으로 된 문자열 (문자 이외의 문자를 처리 할 필요가 없음)을 작성하고 다음과 같이 ANNOUNCER VOICE 변환 알고리즘을 수행하는 함수를 작성하십시오.

  • 먼저 대문자를 모두 사용하십시오.
  • 각 단어마다
    • 연장 각 문자를 세 겹으로 각 자음 클러스터를; 단, 단어 자음 클러스터로 시작 하는 경우를 제외하고 해당 클러스터를 늘리지 마십시오. 예를 들어 other되어야 OTTTHHHEEERRR하지만 mother되어야합니다 MOTTTHHHEEERRR.
    • 연장 을 배로하여 최종 모음입니다.
  • 연신율의 두 경우 모두 , 편지를 3 중으로 묶는 경우 먼저 양쪽에 중복 된 글자와 병합하십시오. 예를 들어 hill이어야 HIIILLL하고 bookkeeper이어야합니다 BOOKKKEEPPPEEERRR.
  • 이 도전의 목적을 위해 y자음으로 간주합니다.
  • 설명 / 단순화 : 각 단어 쌍이 단일 공백으로 구분되고 입력에 연속 공백이없고 입력이 빈 문자열이 아니라고 가정 할 수 있습니다.
  • 최단 코드 승리!

테스트 벡터 :

> sunday sunday
SUNNNDDDAAAYYY SUNNNDDDAAAYYY
> mia hamm
MIAAA HAAAMMM
> chester alan arthur
CHESSSTTTEEERRR ALLLAAANNN ARRRTTTHHHUUURRR
> attention please
ATTTENNNTTTIOOONNN PLEASSSEEE
> supercalifragilisticexpialidocious
SUPPPERRRCCCALLLIFFFRRRAGGGILLLISSSTTTICCCEXXXPPPIALLLIDDDOCCCIOUUUSSS
> moo
MOOO
> Aachen
AACCCHHHEEENNN
> Oooh
OOOHHH
> grifffest
GRIFFFEEESSSTTT
> k
K
> aaaabbbbc
AAAABBBBCCC

오늘 아침에 질문이 마감되었다는 것을 제외하고는 대답으로 이동하는 참조 구현이 있습니다. :피

import itertools,re
def j(s):return re.match('^[AEIOU]+$',s)
def c(s):return ''.join(sum(([h,h,h]for h in[k for k,g in itertools.groupby(s)]),[]))
def v(s):
 while len(s)>=2 and s[-2]==s[-1]:s=s[:-1]
 return s+s[-1]+s[-1]
def a(n):
 r=''
 for w in n.split():
  if r:r+=' '
  ss=re.split('([AEIOU]+)', w.upper())
  for i,s in enumerate(ss):
   r += [v(s),s][any(j(t) for t in ss[i+1:])]if j(s)else[s,c(s)][i>0]
 return r
while 1:print a(raw_input('> '))

2
미래에 대한 요청 : 자음 성단 , 합체신장 과 같은 단어와 문구를 피하십시오 . 나와 같은 영어 원어민이 아닌 사람은 게시물을 이해하기 위해 사전이 필요할 수 있습니다.
Dennis

"길쭉한"모음이어야합니다 :(
Devil 's Advocate

자음 클러스터 란 무엇입니까?
MilkyWay90

답변:


6

APL (Dyalog) , 175 바이트

1' +'R' ''[AEIOU][^AEIOU]+ 'R{m/⍨1,3×2≠/m←⍵.Match}'([AEIOU])\1*([^AEIOU]*? )' ' [AEIOU]' ' [^ AEIOU]+' '([^AEIOU ])\1*'R'\1\1\1\2' '&' '&' '\1\1\1''$| |^'R'  '1(819⌶)⍞

온라인으로 사용해보십시오!

 문자 입력을위한 프롬프트

1(819⌶) 대문자로 변환 (819 ≈ 큰)

 결과를 더 전달하십시오 (문자열과 1을 분리하는 역할을 함)

'$| |^'⎕R' 'R의 eplace :
 결국, 모든 공간, 처음
 두 공간 →

 결과를 더 전달 (두 그룹의 문자열을 분리하는 역할을 함)

'([AEIOU])\1*([^AEIOU]*? )' ' [AEIOU]' ' [^ AEIOU]+' '([^AEIOU ])\1*'⎕R'\1\1\1\2' '&' '&' '\1\1\1'R의 eplace :
 동일한 모음의 수와 비 모음의 수와 공간
 모음에 세 번 →와 수정되지 않은 자음
 공간과 모음
 → 자신
 의 공간과 자음 클러스터
 → 자신
 동일한 자음의 실행
 그 중 → 세 모음

'[AEIOU][^AEIOU]+ '⎕R{... }R의 eplace :
 비 모음의 실행과 공간
 네임 스페이스 다음과 같은 익명 함수의 결과 → 인수로 :
  ⍵.Match 발견 된 텍스트
  m← 것과 할당을 m
  2≠/ 쌍대 다른-에서
   곱하기 세에 의해
  1, 앞에 추가 한
  m/⍨ 사용하는 복제에m

 결과를 더 전달하십시오 (두 문자열을 분리해야 함)

' +'⎕R' 'R의 eplace :
 하나 이상의 공백
 → 하나의 공간

1↓ 첫 글자를 지우십시오 (공백)


이 작동합니까? 1↓' +'⎕R' '⊢'[AEIOU][^AEIOU]+ '⎕R{m/⍨1,3×2≠/m←⍵.Match}'([AEIOU])\1*([^AEIOU]*? )' ' [AEIOU]' ' [^ AEIOU]+' '([^AEIOU ])\1*'⎕R(s,'\2')'&' '&'(s←6⍴'\1')⊢'$| |^'⎕R' '⊢1(819⌶)⍞
Zacharý

^ 작동하면 2 바이트를 절약합니다 ^
Zacharý

5

JS (ES6) 138 134 129 바이트

s=>s.toUpperCase()[r="replace"](/(\w)\1/g,"$1")[r](/[AEIOU](?=[^AEIOU]*( |$))/g,s=>s+s+s)[r](/\B./g,s=>/[AEIOU]/.test(s)?s:s+s+s)

WAAAYYY TOOO MAAANNNYYY BYYYTTTEEESSS. AEIOU3 번 들어 있지만 한 번에 골프를 칠 수는 없습니다.

HyperNeutrino 덕분에 -4 바이트

언 골프

function v(str){
    return str.toUpperCase().replace(/(\w)\1/g,"$1").replace(/[AEIOU](?=[^AEIOU]*( |$))/g,s=>s+s+s).replace(/\B./g,s=>[..."AEIOU"].includes(s)?s:s+s+s);
}

나는 코드를 읽지 않고 쓰고 싶다.


1
"WAAAYYY TOOO MAAANNNYYY BYYYTTTEEESSSS"는 ... APL보다 앞서 있습니다.
Zacharý

내가 JS 모르겠지만, 당신은 대체 할 수 s=>/[AEIOU]/.test(s)와 함께 /[AEIOU]/.test?
musicman523

@ musicman523 슬프게도 아닙니다. 삼항 연산자 설명 문의 조건부이기 때문입니다.
ABot

참고로, 자음 클러스터 처리는 약간 부정확 한 것으로 보입니다. 적절한 출력이 될 것입니다 WAAAYYY TOOO MAAANNNYYY BYTEEESSS(즉, 초기 클러스터를 연장하지 마십시오 BYT).
Quuxplusone

글쎄, 처음에 있었다.
Zacharý

5

APL, 90 바이트

{1↓∊{s←{⍵⊂⍨1,2≠/⍵}⋄x↑⍨¨(3⌈≢¨s⍵)⌊≢¨x←s⍵/⍨(1+2×{⌽<\⌽⍵}∨~∧∨\)⍵∊'AEIOU'}¨w⊂⍨w=⊃w←' ',1(819⌶)⍵}

설명:

  • 1(819⌶)⍵: 대문자로 변환
  • w⊂⍨w=⊃w←' ',: 공간 분할
  • {... : 각 단어마다 ...
    • s←{⍵⊂⍨1,2≠/⍵}: s문자열을 연속되는 일치하는 문자 그룹으로 나누는 함수입니다.
    • ⍵∊'AEIOU': 모음을 표시
    • (... ): 어떤 문자를 3 자로할지 확인
      • ~∧∨\: 첫 모음을 지나는 모든 자음,
      • {⌽<\⌽⍵}: 마지막 모음.
      • : 비트 벡터에 2를 곱하고
      • 1+: 하나를 추가하십시오. 이제 선택한 모든 문자가 3있고 나머지 문자 는 1입니다.
    • ⍵/⍨: 주어진 양만큼 각 문자를 복제
    • x←s: 일치하는 문자열로 나누고에 저장하십시오 x.
    • (3⌈≢¨s⍵): 입력 단어에서 각 일치하는 문자 그룹의 길이 (최대 3)
    • ⌊≢¨:의 최소 및 그룹 길이 x.
    • x↑⍨¨: 각 그룹을 그 길이로 만듭니다
  • 1↓∊: 결과를 평평하게하고 첫 번째 문자 (분할을 돕기 위해 처음에 추가 된 공백)를 삭제합니다.

당신은 Adám을 이겼습니다 ... 와우.
Zacharý

매우 깔끔합니다! 약간 섞어서 프로그램으로 작성하면 (Adám에서 제안한 프롬프트를 사용하여) 15 바이트를 더 줄일 수 있습니다.1↓∊{c/⍨(≢¨g)⌈3×((⌽<\∘⌽)∨~∧∨\)'AEIOU'∊⍨c←⊃¨g←⍵⊂⍨1,2≠/⍵}¨w⊂⍨w=⊃w←' ',1(819⌶)⍞
Gil

3

파이썬, 417 바이트

다음은 파이썬에서 참조 구현입니다. 엄청나게 골프를 치지 않는다.

import itertools,re
def j(s):return re.match('^[AEIOU]+$',s)
def c(s):return ''.join(sum(([h,h,h]for h in[k for k,g in itertools.groupby(s)]),[]))
def v(s):
 while len(s)>=2 and s[-2]==s[-1]:s=s[:-1]
 return s+s[-1]+s[-1]
def a(n):
 r=''
 for w in n.split():
  if r:r+=' '
  ss=re.split('([AEIOU]+)',w.upper())
  for i,s in enumerate(ss):
   r+=[v(s),s][any(j(t) for t in ss[i+1:])]if j(s)else[s,c(s)][i>0]
 return r

다음을 사용하여 테스트하십시오.

while True:
 print a(raw_input('> '))

불필요한 공간을 제거하고로 변경 ss하여 적어도 골프를 조금 더해서 는 안 S됩니까?
Zacharý

2

파이썬 3 , 238 바이트

def f(s):
 s=s.upper();k=[s[0]];s=''.join(k+[s[i]for i in range(1,len(s))if s[i]!=s[i-1]])
 for i in range(1,len(s)):k+=[s[i]]*(3-2*(s[i]in'AEIOU'and i!=max(map(s.rfind,'AEIOU'))))
 return''.join(k)
print(' '.join(map(f,input().split())))

온라인으로 사용해보십시오!


? 로 설정 v하여 바이트를 저장할 수 있습니까 'AEIOU'?
Zacharý

@ Zacharý 고맙지 만 불행히도 바이트 수는 변경되지 않습니다.
HyperNeutrino

아, 첫 번째 공간 v.
Zacharý

0

Perl 5 , 139 + 1 (-p) = 140 바이트

$_=uc,s/^([^AEIOU]*)//,$s=$1,s/([^AEIOU])\1*/$1x(($q=length$&)>3?$q:3)/ge,s/.*?\K([AEIOU])\1*/$1x(($q=length$&)>3?$q:3)/e,print"$s$_ "for@F

온라인으로 사용해보십시오!

예에 따라 "aaaabbbbc"테스트 사례도 처리합니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.