Spoonerise từ trên tiếng Phần Lan


19

Thử thách này dựa trên, và chứa các trường hợp thử nghiệm từ một khóa học lập trình tôi đã học tại Đại học Aalto. Các tài liệu được sử dụng với sự cho phép.

Hai năm rưỡi trước đây đã có một thách thức về tiếng Anh trong tiếng Anh . Tuy nhiên, trong tiếng Phần Lan thì phức tạp hơn nhiều.

Spoonerism ở Phần Lan

Trong tiếng Phần Lan, nguyên âm là aeiouyäövà phụ âm là bcdfghjklmnpqrstvwxz. (å là một phần kỹ thuật của Phần Lan, nhưng không được xem xét ở đây.)

Các từ cơ bản nhất chỉ lấy nguyên âm đầu tiên của mỗi từ và bất kỳ phụ âm nào đứng trước chúng và trao đổi các phần:

henri kontinen -> konri hentinen
tarja halonen -> harja talonen
frakki kontti -> kokki frantti
ovi kello -> kevi ollo

Nguyên âm dài

Một số từ có chứa hai nguyên âm liên tiếp giống nhau. Trong những trường hợp đó, cặp nguyên âm phải được hoán đổi với nguyên âm đầu tiên của từ khác, nguyên âm rút ngắn hoặc kéo dài để giữ nguyên độ dài.

haamu kontti -> koomu hantti
kisko kaappi -> kasko kiippi

Trong trường hợp hai nguyên âm liên tiếp khác nhau, điều này không áp dụng:

hauva kontti -> kouva hantti
puoskari kontti -> kooskari puntti

Ba hoặc nhiều chữ cái liên tiếp sẽ không xuất hiện trong đầu vào.

Nguyên âm hài hòa

Phần Lan có một thứ đáng yêu gọi là hòa âm nguyên âm . Về cơ bản, nó có nghĩa là nguyên âm sau aounguyên âm trước äöy không nên xuất hiện trong cùng một từ.

Khi trao đổi trước hoặc sau nguyên âm vào một từ, tất cả các nguyên âm của các loại khác trong phần còn lại của từ nên được thay đổi để phù hợp với sự khởi đầu mới của từ ( a <-> ä, o <-> ö, u <-> y):

yhä kontti -> kouha ntti
hauva läähättää -> yvä haahattaa

eilà trung tính và có thể xuất hiện với tất cả các chữ cái khác; hoán đổi chúng thành một từ không được gây ra thay đổi cho phần còn lại của từ.

Trường hợp đặc biệt

Nguyên âm hài hòa không áp dụng cho một số từ, bao gồm nhiều từ mượn và từ ghép. Những trường hợp này không bắt buộc phải xử lý "chính xác".

Thử thách

Cho hai từ, xuất ra các từ muỗng.

Các từ đầu vào sẽ chỉ chứa các ký tự a-zäö. Bạn có thể chọn sử dụng chữ hoa hoặc chữ thường, nhưng lựa chọn của bạn phải nhất quán giữa cả hai từ và đầu vào / đầu ra.

I / O có thể được thực hiện trong bất kỳ định dạng thuận tiện . (Các từ nên được coi là chuỗi hoặc mảng ký tự.)

Đây là , vì vậy giải pháp ngắn nhất tính bằng byte sẽ thắng.

Các trường hợp thử nghiệm


Chúng ta có thể chọn mã hóa đầu vào / đầu ra không? Ngoài ra, có thể chấp nhận yêu cầu đầu vào sử dụng kết hợp dấu phụ thay vì các ký tự đơn không?
Doorknob

@Doorknob Bạn có thể chọn bất kỳ mã hóa nào, nhưng văn bản sẽ ở dạng NFC (tức là không có ký tự kết hợp). Mã hóa có thể là trường hợp tương thích với một số ngôn ngữ, nhưng NFC / NFD có thể sẽ không. (Bất cứ điều gì có thể xử lý đều U+0308 COMBINING DIAERESISnên xử lý U+00E4 LATIN SMALL LETTER A WITH DIAERESIStốt.)
PurkkaKoodari

1
eilà trung tính, là fihus keksy, huvu lehylesmä prihticâu trả lời chấp nhận được kehys fiksu, levy huhuprisma lehtitương ứng?
Arnauld

1
Như một nhận xét phụ: vì nguyên âm dài và nguyên âm hài hòa, nên tiếng gõ của Phần Lan không phải là một chức năng không liên quan . Ví dụ : puoskari äyskäri --> äöskäri puuskari --> puoskari ääskäri.
Arnauld

@Arnauld số Tôi sẽ cập nhật câu hỏi; nguyên âm trung tính nên không gây ra thay đổi.
PurkkaKoodari

Câu trả lời:


9

JavaScript (ES6), 196 175 byte

Lấy các từ như hai chuỗi trong cú pháp currying (a)(b). Trả về một mảng gồm hai mảng ký tự.

a=>b=>[(e=/(.*?)([eiäaöoyu])(\2?)(.*)/,g=(a,[,c,v])=>[...c+v+(a[3]&&v)+a[4]].map(c=>(j=e.search(v),i=e.search(c))>9&j>9?e[i&~1|j&1]:c))(a=e.exec(a),b=e.exec(b),e+=e),g(b,a)]

Hãy thử trực tuyến!

Làm sao?

Mỗi từ đầu vào được chuyển qua biểu thức chính quy e , có 4 nhóm bắt giữ:

e = /(.*?)([eiäaöoyu])(\2?)(.*)/    1: leading consonants (or empty)
     [ 1 ][     2    ][ 3 ][ 4]     2: first vowel
                                    3: doubled first vowel (or empty)
                                    4: all remaining characters

Hàm trợ giúp g () lấy tất cả các nhóm bắt giữ của từ được cập nhật dưới dạng [] và các nhóm bắt giữ thứ nhất và thứ hai của từ khác là cv .

Chúng tôi áp dụng nguyên tắc cơ bản và chăm sóc các nguyên âm dài với:

c + v + (a[3] && v) + a[4]

Để áp dụng hòa âm nguyên âm, trước tiên chúng ta ép buộc biểu thức chính quy e vào một chuỗi bằng cách thêm nó vào chính nó, điều này mang lại:

e = "/(.*?)([eiäaöoyu])(\2?)(.*)//(.*?)([eiäaöoyu])(\2?)(.*)/"
     ^^^^^^^^^^^^^^^^
     0123456789ABCDEF (position as hexa)

Nguyên âm cần được hài hòa có vị trí lớn hơn 9 trong chuỗi kết quả. Hơn nữa, khái niệm được sắp xếp theo một cách mà nguyên âm trước äöy được đặt tại vị trí thậm chí, khi trở lại nguyên âm aou được đặt tại vị trí lẻ, bên cạnh các đối tác của họ.

Do đó, công thức dịch sau đây được áp dụng cho từng ký tự c của từ đầu ra:

(j = e.search(v), i = e.search(c)) > 9 & j > 9 ? e[i & ~1 | j & 1] : c

4

Python 3 , 235 231 225 221 217 215 byte

import re
S=F,B='äöy','aou'
def f(a,b,C=1):
 e,r,Q,W=re.findall(fr' ?(.*?([ei{B+F}]))(\2)?(\w*)'*2,a+' '+b)[0][2:6]
 for c in zip(*S*(W in B)+(B,F)*(W in F)):r=r.replace(*c)
 return[Q+W*len(e)+r]+(C and f(b,a,[]))

Hãy thử trực tuyến!


Đã lưu

  • -2 byte, nhờ Lynn
  • -4 byte, nhờ Zacharý

2
Lưu hai byte với:fr' ?(.*?([ei{B+F}]))(\2)?(\w*)'
Lynn

1
Thậm chí tốt hơn: bạn có thể thay đổi dòng thứ hai thành S='äöy','aou', sau đó trên dòng thứ năm: (F,B)=> S(B,F)=> S[::-1](Điều này không tương thích với đề xuất @Lynn đưa ra)
Zacharý

Ngoài ra, bạn có thể thay đổi dòng thứ tư thành e,r,Q,W=re.findall(r' ?(.*?([eiaouäöy]))(\2)?(\w*)'*2,a+' '+b)[0][2:5]một vài byte được lưu.
Zacharý

Điều tôi muốn nói: dòng thứ 2 thành S=F,B='aöy','aou', và sau đó trên dòng thứ 4 đổi (F,B)thành S.
Zacharý

S=F,B=...nên lưu một vài byte nếu bạn thay thế (F,B)bằngS
Zacharý

0

Bình thường, 84 byte

.b++hY*W@N2JhtY2XW}JeA@DJc2"aouäöy"eNGH_Bmth:d:"^([^A*)([A)(\\2)*(.+)"\A"aeiouyäö]"4

Hãy thử trực tuyến. Bộ thử nghiệm.

Chứng minh rằng nó không phải khó khăn trong ngôn ngữ golf. Một ngôn ngữ dựa trên ngăn xếp có thể làm tốt hơn nữa.

Pyth sử dụng ISO-8859-1 theo mặc định, äömỗi byte cũng vậy.

Giải trình

  • Q, chứa cặp từ đầu vào, được thêm vào ngầm.
  • m: ánh xạ từng từ dtrong đầu vào thành:
    • :"^([^A*)([A)(\\2)*(.+)"\A"aeiouyäö]": thay thế Abằng aeiouyäö]trong chuỗi để lấy regex ^([^aeiouyäö]*)([aeiouyäö])(\2)*(.+).
    • :d: tìm tất cả các trận đấu và trả lại các nhóm bắt giữ của họ.
    • h: lấy trận đấu đầu tiên (và duy nhất).
    • t: thả nhóm đầu tiên chứa toàn bộ trận đấu.
  • _B: ghép với ngược lại để có được [[first, second], [second, first]] .
  • .b: ánh xạ từng cặp từ N, Y trong đó sang:
    • hY: lấy phụ âm đầu của từ thứ hai.
    • @N2: lấy nguyên âm đầu tiên dài của từ đầu tiên, hoặc None .
    • htY: lấy nguyên âm đầu tiên của từ thứ hai.
    • J: lưu nó vào J.
    • *WLiên 2: nếu có một nguyên âm dài, hãy nhân đôi nguyên âm của từ thứ hai.
    • +: nối nó với các phụ âm.
    • c2"aouäöy": chia làm aouäöyhai để có được ["aou", "äöy"].
    • @DJ: sắp xếp cặp theo giao điểm với nguyên âm đầu tiên của từ thứ hai. Điều này có được một nửa với nguyên âm đầu tiên của từ thứ hai ở cuối cặp.
    • A: lưu cặp vào G, H.
    • e: lấy nửa sau.
    • }J: xem nguyên âm đầu tiên của từ thứ hai có ở nửa sau không.
    • XWLiên eNGH: nếu có, ánh xạ Gtới Hhậu tố của từ đầu tiên, nếu không thì giữ nguyên hậu tố.
    • +: nối thêm hậu tố.
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.