คุณคือ Romanizer ที่รัก


38

สุริยวรมันที่ญี่ปุ่นกำลังแปลงข้อความภาษาญี่ปุ่นเป็นตัวอักษรละติน ในการท้าทายนี้คุณจะได้รับสตริงอักขระภาษาญี่ปุ่นเป็นอินพุตและคาดว่าจะแปลงเป็นสตริง ASCII ที่ถูกต้อง

สิ่งที่คุณต้องรู้

ภาษาญี่ปุ่นมีระบบการเขียนสามระบบ: ฮิระงะนะ (ระบบโค้งใช้สำหรับคำศัพท์สั้น ๆ ) คาตาคานะ (ระบบมุม - y ใช้สำหรับเสียงและคำที่ยืมมาจากภาษาอื่น) และคันจิ (ตัวอักษรหนาแน่นจากจีน) ในการท้าทายนี้เราจะกังวลเกี่ยวกับฮิรางานะเท่านั้น

ในพยางค์ฮิระงะนะมีทั้งหมด 46 ตัวอักษร ตัวละครแต่ละตัวแทนพยางค์ ตัวละครถูกจัดระเบียบโดยเสียงแรก (พยัญชนะ) และเสียงที่สอง (สระ) aiueoคอลัมน์ในการสั่งซื้อ

 : あいうえお
k: かきくけこ
s: さしすせそ
t: たちつてと
n: なにぬねの
h: はひふへほ
m: まみむめも
y: や ゆ よ
r: らりるれろ
w: わ   を
N: ん

(หากคุณคัดลอกและวางตารางนี้โปรดทราบว่าฉันได้ใช้ช่องว่างในเชิงอุดมการณ์ U + 3000 เพื่อเว้นวรรค y และ w)

ดังนั้นสำหรับตัวอย่างเช่นあとめatomeควรผลิตการส่งออกของ ตัวอักษรตัวแรกเป็นaที่สองคือและคนที่สามคือtome

ข้อยกเว้น

เช่นเดียวกับภาษาที่ดีใด ๆ ภาษาญี่ปุ่นมีข้อยกเว้นกฎของมันและตารางฮิรางานะมีหลาย อักขระเหล่านี้มีความเด่นชัดแตกต่างจากตำแหน่งของพวกเขาในตารางเล็กน้อยซึ่งแปลว่า:

し: shiไม่ใช่si
ち: chiไม่ใช่ti
つ: tsuไม่ใช่tu
ふ: fuไม่ใช่hu

Dakuten ゛

คำว่า 'dakuten' หมายถึง 'เครื่องหมายโคลน': dakuten เปลี่ยนเสียงเป็นเสียงที่เปล่งออกมาเทียบเท่า (ปกติ); ตัวอย่างเช่นかkaกลายเป็น gaか゛ รายการเปลี่ยนแปลงทั้งหมด:

k→การg
s→การz
t→การd
h→การb

ข้อยกเว้นมีการเปลี่ยนแปลงเช่นกัน: し゛: ji(หรือzhi), ไม่zi
ち゛: ji, ไม่di
つ゛: dzu, ไม่du
(ふ゛ทำตามที่คุณคาดหวัง; ไม่ใช่ข้อยกเว้น)

Handakuten เป็นอักขระเพิ่มเติม゜ที่ใช้กับhแถว ถ้าวางอยู่หลังตัวละครจะเปลี่ยนเสียงของตัวละครไปมากกว่าpb

ทั้ง dakuten และ handakuten จะได้รับเป็นอักขระแต่ละตัว คุณไม่จำเป็นต้องจัดการกับแบบฟอร์มที่ precomposed หรือตัวละครรวม

ตัวละครขนาดเล็ก

ในที่สุดก็มีตัวละครบางเวอร์ชั่นขนาดเล็ก พวกเขาแก้ไขตัวละครที่มาก่อนหรือหลังพวกเขา

ゃゅょ

เหล่านี้เป็นรูปแบบที่เล็ก ๆya, และyu yoพวกมันถูกวางหลังจากเสียงในi-column เท่านั้น พวกเขาลบiและเพิ่มเสียงของพวกเขา ดังนั้นきやกลายเป็นkiya; きゃkyaกลายเป็น

หากวางไว้หลังchiหรือshi(หรือแบบฟอร์ม dakuten-ed) yจะถูกลบออกด้วย しゆคือshiyu; しゅshuมี

tsuสิ่งสุดท้ายที่คุณจะต้องจัดการกับเป็นขนาดเล็ก cons ตัวสะกดที่เพิ่มขึ้นเป็นสองเท่าไม่ว่าจะเกิดอะไรขึ้น มันไม่ทำอะไรเลย ตัวอย่างเช่นきたคือkita; きったkittaมี

สรุปอินพุตและเอาต์พุต

โปรแกรมของคุณจะต้องสามารถถอดเสียงได้: ฮิระงะนะพื้นฐาน 46 รูปแบบ dakuten และ handakuten และชุดค่าผสมที่มีตัวอักษรขนาดเล็ก

พฤติกรรมที่ไม่ได้กำหนดรวมถึง: small ya, yuและyoไม่ใช่หลังจากตัวละครที่มีiขนาดเล็กtsuที่ส่วนท้ายของสตริง, dakuten กับตัวละครที่ไม่ได้รับผลกระทบ, handakuten ที่ไม่ใช่pตัวละคร, และสิ่งอื่น ๆ ที่ไม่ได้กล่าวถึงใน

คุณอาจจะสมมติว่าอินพุตทั้งหมดนั้นถูกต้องและมีเพียงตัวอักษรญี่ปุ่นที่กล่าวถึงข้างต้น

เคสไม่สำคัญในเอาต์พุต คุณยังอาจแทนที่rด้วยlหรือคนเดียวกับn mเอาต์พุตสามารถมีหนึ่งช่องว่างระหว่างทุกพยางค์หรือไม่มีช่องว่างเลย

นี่คือ : รหัสที่สั้นที่สุดในหน่วยไบต์ชนะ

กรณีทดสอบ

กรณีทดสอบจำนวนมากสำหรับแต่ละส่วนจะได้รับในสเป็ค บางกรณีเพิ่มเติม:

ならか゛な→ hiragana

かたかな→ katakana

ん゛いき゛ゃんんんんんんんんんんん daigyakutensaiban

ふ゜ろく゛らふふふふふふふふふふふふふふふふふふふふふふふふ puroguramingupazurucoudogorufu

て゛んほ゛って→ ganbatte

หมายเหตุ

  • ฉันไม่รู้ภาษาญี่ปุ่นมากนอกจากสิ่งที่ฉันเขียนที่นี่ โปรดแจ้งให้เราทราบหากฉันทำผิดพลาด

  • เดิมทีฉันวางแผนที่จะรวมคาตาคานะด้วย (ดังนั้นกรณีทดสอบการถอดเสียงภาษาอังกฤษของฉันอาจแม่นยำกว่านี้เล็กน้อย ) แต่นั่นอาจจะมากเกินไปสำหรับความท้าทายของรหัสกอล์ฟ

  • ชื่อ Unicode รวมถึงการทับศัพท์ของอักขระแต่ละตัวแยกกัน แต่ไม่มีข้อยกเว้น สิ่งนี้อาจเป็นประโยชน์กับคุณหรือไม่ก็ได้

  • ขอบคุณ squeamishossifrage สำหรับการแก้ไขความผิดพลาดสองประการ!

  • ฉันขอโทษถ้ามันยาวเกินไป ฉันพยายามใส่ฮิระงะนะส่วนใหญ่ให้เข้ากับความท้าทาย แต่บางสิ่ง (เช่นฮิระงะนะเฉพาะสระเล็กการเปลี่ยน n เป็น m ต่อหน้าพยัญชนะบางตัวและเครื่องหมายการทำซ้ำ) ต้องถูกตัดออกเพื่อรักษาความท้าทายที่จัดการ

  • ฉันไม่เสียใจเลยสำหรับชื่อเรื่อง มันเป็นงานชิ้นเอก


1
สิ่งที่ควรจะแสดงผลสำหรับきっった?
lirtosiast

@Thomas: นั่นเป็นอินพุตที่ไม่ถูกต้อง เอาต์พุตสามารถเป็นอะไรก็ได้ที่คุณต้องการ
Deusovi

1
ควรっしจะเป็นsshiหรือshshi?
lirtosiast

2
I'm not at all sorry for the title. It's a masterpiece.Downvoted
ทำให้เสียชีวิต

3
@ ทำให้ไม่ต้องนำอคติต่อต้านบริทนีย์ของคุณมาที่นี่ แม้ว่าโดยส่วนตัวแล้วฉันอาจจะเป็นแฟน J-Lo มากกว่า แต่ฉันจะไม่ลงคะแนนปริศนาที่ยอดเยี่ยมในเรื่องนั้น
รอบนอก

คำตอบ:


7

Python 2, 638 ไบต์

import unicodedata
s=input()
k=[0x309B,0x309C,0x3063]
m=[0x3083,0x3085,0x3087]
e={0x3057:'shi',0x3061:'chi',0x3064:'tsu',0x3075:'fu'}
d={0x3057:'ji',0x3061:'ji',0x3064:'dzu'}
D=dict(zip('ksth','gzdb'))
f=lambda c:unicodedata.name(c).split()[-1].lower()if ord(c)not in e else e[ord(c)]
g=lambda c:d[c]if c in d else D[f(c)[0]]+f(c)[1:]
R=[]
r=[]
t=[]
i=0
while i<len(s):
 c=ord(s[i])
 if c==k[0]:R[-1]=g(s[i-1])
 elif c==k[1]:R[-1]='p'+R[-1][1:]
 elif c in m:R[-1]=R[-1][:-1];n=f(s[i]);R+=[n[1:]]if r[-1]in[0x3057,0x3061]else[n];r+=[c]
 elif c==k[2]:t+=[len(R)]
 else:R+=[f(s[i])];r+=[c]
 i+=1
for i in t:R[i]=R[i][0]+R[i]
print ''.join(R)

รับอินพุตเป็นสตริง Unicode

ทดสอบบนIdeone


1
คุณสามารถบันทึกลาก่อนได้โดยเปลี่ยนprint ''.join(R)เป็นprint''.join(R)
Zacharý

6

Python 2, 447 ไบต์

import unicodedata as u
r=str.replace
i=''.join('x'*('SM'in u.name(x)or ord(x)==12444)+u.name(x)[-2:].strip()for x in raw_input().decode('utf-8'))
for a,o in zip('KSTH','GZDB'):
    for b in'AEIOU':i=r(r(i,a+b+'xRK','P'+b),a+b+'RK',o+b)
for a,b,c,d in zip('STDZ',('SH','CH','J','J'),'TDHH',('TS','DZ','F','F')):i=r(r(i,a+'I',b+'I'),c+'U',d+'U')
for a in'CH','SH','J':i=r(i,a+'IxY',a)
for a in'BCDFGHJKMNPRSTWYZ':i=r(i,'xTSU'+a,a+a)
print r(i,'Ix','')

สิ่งนี้ใช้อินพุต Unicode โดยตรงซึ่งทำให้ฉันสูญเสียสองสามไบต์เพราะdecode('utf-8')แต่ฉันคิดว่ามันเป็นจิตวิญญาณของความท้าทายมากกว่า

ฉันเริ่มต้นด้วยการแทนที่ตัวละครทุกตัวด้วยอักขระสองตัวสุดท้ายของชื่อ unicode ตามที่แนะนำในบันทึกย่อของปริศนา น่าเสียดายที่นี่ไม่ได้แยกความแตกต่างระหว่างตัวละครรุ่นอื่นของตัวละครเดียวกันดังนั้นฉันต้องทำการแฮ็กที่น่าเกลียดเพื่อเพิ่ม 'x' ก่อนตัวละครตัวเล็กและ handakuten

ส่วนที่เหลือของลูปเป็นเพียงการแก้ไขข้อยกเว้นตามลำดับ:

  1. ครั้งแรกสำหรับวงเปลี่ยน dakutens และ handakutens เป็นพยัญชนะที่ถูกต้อง;
  2. ข้อที่สองสำหรับข้อตกลงแบบวนซ้ำกับข้อยกเว้นฮิรางานะของชิชิชิและฟู
  3. ที่สามสำหรับข้อตกลงห่วงกับข้อยกเว้นก่อนที่ตัวอักษร y- ขนาดเล็ก (เช่น sha, jo);
  4. ที่สี่สำหรับข้อตกลงห่วงกับพยัญชนะสองเท่าหลังจาก Tsu ขนาดเล็ก
  5. บรรทัดสุดท้ายเกี่ยวข้องกับ y- ขนาดเล็ก

ฉันหวังว่าฉันจะได้รวมขั้นตอนมากขึ้น แต่ในบางกรณีขั้นตอนจะต้องมีการดำเนินการเพื่อหลีกเลี่ยงความขัดแย้ง

ลองออนไลน์! (เวอร์ชันหลายคู่สายพร้อมตัวอย่างเพิ่มเติมสามารถดูได้ที่นี่ )



ยินดีต้อนรับสู่ PPCG วิธีแก้ปัญหาแรกที่ดีมาก :)
Shaggy

เปลี่ยนช่องว่างทั้งสี่ด้านหน้าของคุณfor b in'AEIOU'เป็นแท็บหรือเว้นวรรคเดียวเพื่อประหยัด 3 ไบต์ คุณอาจสามารถใช้from unicodedata import*เพื่อบันทึกไบต์บางอย่าง - ไม่แน่ใจ
สตีเฟ่น

4

Swift 3, 67 64 ตัวอักษร

ให้ r = {(s: String) ใน s.applyingTransform (.toLatin, reverse: false)}

let r={(s:String)in s.applyingTransform(.toLatin,reverse:false)}

3
builtin จริงๆแล้ว Swift มี BUILTIN สำหรับสิ่งนี้หรือไม่?
Zacharý

ไม่รู้จัก Swift เลย แต่คุณสามารถตัดช่องว่างหลังจากs:String)และ.toLatin,?
Yytsi

@ TuukkaX เห็นดี!
idrougge

@ ZacharýดีFoundationมี
idrougge

3

Python 3 , 259 ไบต์

import re,unicodedata as u
s=re.sub
n=u.normalize
k,*r=r'NFKC DZU DU TSU TU \1\1 SM.{6}(.) \1 (CH|J|SH)Y \1 ISMALL.(Y.) CHI TI JI [ZD]I SHI SI FU HU'.split()
t=''.join(u.name(c)[16:]for c in n(k,s(' ','',n(k,input()))))
while r:t=s(r.pop(),r.pop(),t)
print(t)

ลองออนไลน์!

คำอธิบาย

เราโชคดีกับรูปแบบอินพุตนี้! ดูว่าเกิดอะไรขึ้นถ้าฉันส่งอินพุตผ่านการปรับสภาพ NFKC :

>>> nfkc = lambda x: u.normalize('NFKC', x)
>>> [u.name(c) for c in 'は゛']
['HIRAGANA LETTER HA', 'KATAKANA-HIRAGANA VOICED SOUND MARK']
>>> [u.name(c) for c in nfkc('は゛')]
['HIRAGANA LETTER HA', 'SPACE', 'COMBINING KATAKANA-HIRAGANA VOICED SOUND MARK']

dakuten ถูกแทนที่ด้วยช่องว่างและรวม dakuten ตอนนี้พื้นที่นั้นคือทั้งหมดที่แยก d ออกจาก dakuten ของมัน ดังนั้นเราจึงกำจัดมันและทำให้เป็นปกติอีกครั้ง :

>>> [u.name(c) for c in nfkc(nfkc('は゛').replace(' ', ''))]
['HIRAGANA LETTER BA']

การเล่นชนิดหนึ่ง บรรทัดที่ห้าเปลี่ยนอินพุตให้เป็นสิ่งที่ต้องการ

KONOSUBARASIISEKAINISISMALL YUKUHUKUWO

จากนั้นเราใช้การแทนที่ regex 9 อันน่าเบื่อที่อัดแน่นไปrด้วยและเราเสร็จแล้ว:

KONOSUBARASHIISEKAINISHUKUFUKUWO

(Jonathan French บันทึก 4 ไบต์เขียนimport re,unicodedata as uแทนimport re;from unicodedata import*ขอขอบคุณ!)


การใช้บรรทัดฐานในทางที่ผิดเพื่อความสนุกสนานและผลกำไร นั่นเป็นสิ่งที่สวยงาม
ทิม Pederick

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.