เขียนโค้ดเข้ารหัส VIC


18

ตัวเลข VICเป็นหนึ่งในผู้ที่มีความซับซ้อนมากที่สุดดินสอและกระดาษยันต์เคยวางแผน ใช้ในยุค 50 โดยสายลับโซเวียต Reino Häyhänenชื่อรหัสว่า "VICTOR" หลักการสำคัญคือความปลอดภัยผ่านการทำให้งงงวย; จำนวนมากของ obfuscation

งานของคุณคือการเขียนโปรแกรมหรือฟังก์ชั่นที่จะรับข้อความและเข้ารหัสโดยใช้รหัส VIC ฉันยังได้โพสต์ความท้าทาย VIC เข้ารหัสถอดรหัสที่นี่ หากคำแนะนำใด ๆ ต่อไปนี้ไม่ชัดเจนอย่าลังเลที่จะถามพวกเขาในความคิดเห็น คำแนะนำถูกดัดแปลงจากเว็บไซต์นี้

การเข้ารหัสรหัส VIC

การจัดเตรียม

คุณจะต้องมีห้าอินพุต:

  • ข้อความธรรมดา
  • คำหลักหรือวลีสั้น ๆ ที่มีตัวอักษรที่พบบ่อยที่สุดในภาษาของคุณ
  • วลีสำคัญเช่นคำพูดหรือบรรทัดจากเพลง (อย่างน้อย 20 ตัวอักษร)
  • วันที่ (หรือตัวเลขอื่นที่เป็นตัวเลขหกหลักหรือมากกว่า)
  • หมายเลขตัวแทนส่วนตัว

ในทางปฏิบัติผู้ส่งและผู้รับสี่คนสุดท้ายควรได้รับการตกลงกันล่วงหน้ารวมถึงไม่ว่าจะใช้หมายเลขตัวแทนของผู้ส่งหรือผู้รับในการเข้ารหัส

ข้อความตัวอย่างของฉันจะเป็น: We are discovered. Take what you can. Burn everything else. Move to Safehouse Foxtrot 3.

เราจะได้รับการเข้ารหัสในภาษาอังกฤษ (แม้ว่าคุณอาจจะใช้สิ่งที่ภาษาและอักษรที่คุณต้องการ) A, E, I, N, O, R, S, Tและตัวอักษรที่พบมากที่สุดในตัวอักษรภาษาอังกฤษ SENATORIผมจะใช้คำหลัก

วลีสำคัญของฉันคือคำพูดของ Richard Feynman: "หลักการแรกคือคุณต้องไม่หลอกตัวเอง - และคุณเป็นคนที่ง่ายที่สุดที่จะหลอก"

เป็นวันที่ฉันจะใช้วันที่ 31 กรกฎาคม 2016 (ในรูปแบบ3172016) ซึ่งเป็นวันที่เมื่อฉันเขียนคำอธิบายนี้

9จำนวนบุคคลที่ฉันได้รับการแต่งตั้งให้ตัวเองเป็น

สรุปขั้นตอน

  1. รับคีย์กลางสำหรับใช้ในขั้นตอนต่อไปนี้
  2. สร้างและใช้กระดานหมากรุกแบบ straddling
  3. สร้างและใช้ตารางการขนย้ายแรก
  4. สร้างและใช้ตารางการขนย้ายที่สอง (กระจัดกระจาย)
  5. จบข้อความด้วยการแทรกกลุ่มตัวบ่งชี้ข้อความ

Submechanisms

อีกสองสิ่งที่จะอธิบายก่อนที่เราจะเข้าสู่เนื้อของเรื่อง: กระบวนการของการเติมห่วงโซ่และลำดับ

การเพิ่มเครือข่ายหรือที่รู้จักกันในชื่อตัวกำเนิด Fibonacci ที่ล้าหลังทำงานโดยใช้ลำดับตัวเลขเริ่มต้นเพิ่มตัวเลขสองหลักแรกโดยไม่ต้องถือ (เพิ่มเข้าด้วยกันแล้วmod 10) และต่อท้ายผลลัพธ์ ตัวอย่างเช่น:

79081
7 + 9 = 6

790816
9 + 0 = 9

7908169
0 + 8 = 8

79081698
8 + 1 = 9

790816989
1 + 6 = 7

7908169897
... and so on

การจัดลำดับเป็นหลักคือการเรียงลำดับตัวอักษรหรือตัวเลขและติดฉลากตามลำดับตัวอักษร / ตัวเลข รายการที่ซ้ำกันมีป้ายกำกับจากซ้ายไปขวา ตัวอย่างเช่น:

E X A M P L E
    0           # A
1   0       2   # Es
1   0     3 2   # L
1   0 4   3 2   # M
1   0 4 5 3 2   # P
1 6 0 4 5 3 2   # X

3  3  0  5  8  4  2  0  4  7  5  4  8  1
      0              1                     # 0s
      0              1                 2   # 1
      0           3  1                 2   # 2
4  5  0           3  1                 2   # 3s
4  5  0        6  3  1  7        8     2   # 4s
4  5  0  9     6  3  1  7    10  8     2   # 5s
4  5  0  9     6  3  1  7 11 10  8     2   # 7
4  5  0  9 12  6  3  1  7 11 10  8 13  2   # 8s

ฉันใช้การจัดทำดัชนีเป็นศูนย์ที่นี่ แต่ทำดัชนีตามที่คุณต้องการ

1. คีย์ระดับกลาง

แยก 20 ตัวอักษรตัวแรกของวลีที่สำคัญออกเป็นสองกลุ่ม 10 และ sequentialize แต่ละคนซึ่งเราจะเรียกและS1S2

    THEFIRSTPR
S1: 8201357946

    INCIPLEIST
S2: 2603751489

เลือกตัวระบุข้อความ 5 หลักแบบสุ่มM(ซึ่งอาจเป็นหนึ่งในอินพุตหากคุณต้องการ):

M = 47921

ลบโดยไม่ต้องยืม (ลบmod 10) ตัวเลขห้าหลักแรกของวันที่หลัก3172016จากM:

M      47921
date - 31720
     = 16201

เชนเพิ่มผลลัพธ์จนกว่าคุณจะมีสิบหลัก:

1620178218

เพิ่มตัวเลขเหล่านี้ไปยังS1โดยไม่ต้องดำเนินการหรือที่mod 10จะได้รับG :

     1620178218
S1 + 8201357946
G  = 9821425154

ดังกล่าวข้างต้นS2เขียนลำดับ 0123456789 ค้นหาหลักของแต่ละGลำดับ 0123456789 S2และแทนที่ด้วยหลักตรงด้านล่างของมันใน ผลที่ได้คือTผลที่ได้คือ

   0123456789
S2 2603751489

G  9821425154
T  9806705657

ใช้การเพิ่มโซ่เพื่อขยาย Tถึง 60 หลัก

9806705657

becomes

980670565778637511245490262369939288595822106344304316978734

เหล่านี้ 50 หลักสุดท้ายในห้าแถวสิบหลักแต่ละรูปแบบ Uบล็อก

T  9806705657
U  7863751124
   5490262369
   9392885958
   2210634430
   4316978734

ตัวเลขสองหลักสุดท้ายที่ไม่เท่ากับของ Uบล็อกที่มีการเพิ่มจำนวนเป็นรายบุคคลเพื่อบุคคลของตัวแทนในการให้ความกว้างของทั้งสอง transpositions ที่และpq

9 + 3 = 12 (p, ความกว้างของการย้ายครั้งแรก) 9 + 4 = 13 (q, ความกว้างของการถ่ายโอนที่สอง)

จัดลำดับTและใช้ลำดับนี้เพื่อคัดลอกคอลัมน์ของUบล็อกจากบนลงล่างสู่แถวของตัวเลขVใหม่

T     9806705657
seqT  9804612537

U     7863751124
      5490262369
      9392885958
      2210634430
      4316978734

V     69911 56837 12548 26533 30206 13947 72869 49804 84323 75924

Sequentialize แรกpตัวเลขที่จะได้รับที่สำคัญสำหรับการขนย้ายครั้งแรกK1และต่อไปนี้ตัวเลขสำหรับคีย์ที่สองqK2

First 12  6  9  9  1  1  5  6  8  3  7  1  2
K1        6 10 11  0  1  5  7  9  4  8  2  3

Next 13   5  4  8  2  6  5  3  3  3  0  2  0  6
K2        8  7 12  2 10  9  4  5  6  0  3  1 11

ในที่สุดให้เรียงลำดับแถวสุดท้ายของUบล็อกเพื่อให้ได้Cส่วนหัวคอลัมน์สำหรับตารางหมากรุก:

U5  4316978734
C   3105968724

2. กระดานหมากรุก Straddling

ก่อนอื่นฉันจะให้กระดานตรวจสอบตัวอย่างของฉันจากนั้นอธิบายหลักการในการสร้างมันในแบบนั้น:

  3 1 0 5 9 6 8 7 2 4
  S E N A T O R I
2 B D G J L P U W Y .
4 C F H K M Q V X Z #

SENATORIบรรทัดแรกของตัวอักษรเป็นคำสำคัญสั้น ๆ ของเรา คำหลักของคุณสามารถเป็นสตริงใด ๆ โดยไม่ซ้ำกัน แต่เนื่องจากมันเป็นตัวกำหนดแถวบนของกระดานหมากรุกของคุณให้เลือกอย่างชาญฉลาด เหนือคำหลักคือCและแถวอื่น ๆ คือตัวอักษรที่เหลือของคุณตามลำดับที่คุณเลือก ในกรณีของฉันฉันเต็มกระดานหมากรุกกับส่วนที่เหลือของตัวอักษรละตินเครื่องหมายวรรคตอน.และเครื่องหมายสำหรับ demarcating #ตัวเลข โดยพื้นฐานแล้วกระดานหมากรุกเป็นรหัสตัวเลขแฟนซี ยกตัวอย่างเช่น "E" จะถูกแทนที่ด้วย1และ "W" 27จะถูกแทนที่ด้วย

เมื่อเราเข้ารหัสข้อความธรรมดาของเราด้วยกระดานหมากรุกนี้ แต่ก่อนอื่นเราต้องทำให้ข้อความเริ่มต้นของเราชัดเจนน้อยลงโดยการแยกมันในตำแหน่งที่สุ่มและทำให้มันเป็นตัวพิมพ์ใหญ่ทั้งหมด เพื่อแสดงจุดเริ่มต้นดั้งเดิมอื่น ๆ เราใช้สองจุด..

We are discovered. Take what you can. Burn everything else. Move to Safehouse Foxtrot 3.

กลายเป็น

HING ELSE. MOVE TO SAFEHOUSE FOXTROT#3#.. WE ARE
DISCOVERED. TAKE WHAT YOU CAN. BURN EVERYT

เราเข้ารหัสด้วยตารางหมากรุกให้เรา:

407020 1293124 496481 96 354114062831 416479869443442424 271 581 
2173436481812124 95451 274059 22628 435024 232880 14818229

หากความยาวของข้อความไม่สามารถหารด้วย 5 ได้เราจะเพิ่มตัวอักษร null เพื่อตัดข้อความ ข้อความของเรามีความยาว 109 หลักดังนั้นฉันจะเพิ่มหนึ่ง null: "4"

40702 01293 12449 64819 63541 14062 83141 64798 69443 44242 42715
81217 34364 81812 12495 45127 40592 26284 35024 23288 01481 82294

หมายเหตุ: เนื่องจากข้อความตัวอย่างของฉันไม่มีตัวเลขฉันจะบอกที่นี่ว่าคุณอาจกำหนดพูดตาม#3#ที่ถูกเข้ารหัสเป็น44344ที่นี่

3. การขนย้ายครั้งแรก

สร้างตารางการย้ายข้อมูลโดยการเขียนK1(จากส่วน Intermediate Keys) ตามด้วยข้อความที่เข้ารหัสจากขั้นตอนก่อนหน้านี้ในแถวที่มีความยาวเท่ากันใต้คีย์:

K1   6 10 11  0  1  5  7  9  4  8  2  3

     4  0  7  0  2  0  1  2  9  3  1  2
     4  4  9  6  4  8  1  9  6  3  5  4
     1  1  4  0  6  2  8  3  1  4  1  6
     4  7  9  8  6  9  4  4  3  4  4  2
     4  2  4  2  7  1  5  8  1  2  1  7
     3  4  3  6  4  8  1  8  1  2  1  2
     4  9  5  4  5  1  2  7  4  0  5  9
     2  2  6  2  8  4  3  5  0  2  4  2
     3  2  8  8  0  1  4  8  1  8  2  2
     9  4

รับคอลัมน์ตัวเลขตามลำดับหมายเลขที่เราได้รับ:

060826428  246674580  151411542  246272922  961311401  082918141
4414434239 118451234  334422028  293488758  0417249224 794943568

4. การขนย้ายครั้งที่สอง

การขนย้ายครั้งแรกค่อนข้างง่าย อย่างไรก็ตามอันนี้เป็นการขนย้ายที่หยุดชะงัก รูปแบบการหยุดชะงักจะพิจารณาจากความกว้างของตารางและคีย์ ในตัวอย่างของเราเรามี 110 หลักและ 13 คอลัมน์ซึ่งหมายความว่าเราจะมี 8 แถวเต็มและ 6 ที่เหลือ เราเริ่มกรอกข้อมูลในแถวแรก แต่หยุดที่คอลัมน์ 0 และดำเนินการดังนี้:

K2   8  7 12  2 10  9  4  5  6  0  3  1 11

     0  6  0  8  2  6  4  2  8              stop at 0
     2  4  6  6  7  4  5  8  0  1           continue in a triangle pattern
     5  1  4  1  1  5  4  2  2  4  6
     2  7  2  9  2  2  9  6  1  3  1  1
     4  0  1  0  8  2  9  1  8  1  4  1  4  until the end
     4  1  4  4  3  4  2  3  9  1  1        restart and stop at 1
     8  4  5  1  2  3  4  3  3  4  4  2
     2  0  2  8  2  9  3  4  8  8  7  5  8
     0  4  1                                restart and stop at 2

จากนั้นเราเติมช่องว่างสองสามสุดท้ายด้วยตัวเลขที่เหลือ

K2   8  7 12  2 10  9  4  5  6  0  3  1 11

     0  6  0  8  2  6  4  2  8  7  2  4  9
     2  4  6  6  7  4  5  8  0  1  2  2  4
     5  1  4  1  1  5  4  2  2  4  6  7  9
     2  7  2  9  2  2  9  6  1  3  1  1  4
     4  0  1  0  8  2  9  1  8  1  4  1  4
     4  1  4  4  3  4  2  3  9  1  1  9  4
     8  4  5  1  2  3  4  3  3  4  4  2  3
     2  0  2  8  2  9  3  4  8  8  7  5  8
     0  4  1  5  6  8

ตอนนี้เราอ่านคอลัมน์ในแบบเดียวกับที่เราทำในการขนย้ายครั้งแรก

71431148  42711925  861904185 22614147  45499243  28261334  80218938
641701404 025244820 645224398 271283226 94944438  064214521

และแบ่งทุกอย่างออกเป็นกลุ่ม 5 หลัก:

71431 14842 71192 58619 04185 22614 14745 49924 32826 13348 02189
38641 70140 40252 44820 64522 43982 71283 22694 94443 80642 14521

5. จบข้อความ

ขั้นตอนสุดท้ายคือการแทรกตัวระบุข้อความแบบสุ่มของเรา47921ลงในข้อความ ตัวเลขสุดท้ายของวันที่สำคัญ6แสดงระยะทางที่กลุ่มควรมาจากจุดสิ้นสุด

71431 14842 71192 58619 04185 22614 14745 49924 32826 13348 02189 38641
70140 40252 44820 64522 43982 47921 71283 22694 94443 80642 14521

หมายเหตุสำหรับความท้าทายนี้

  • คุณจะได้รับอย่างน้อยห้าอินพุต: ข้อความคำหลักตัวอักษรวลีสำคัญวันที่และหมายเลขส่วนบุคคล คุณอาจรวมสองอินพุตเพิ่มเติม: ตัวระบุข้อความแบบสุ่มและโมฆะที่จำเป็นในการวางข้อความหรือฟังก์ชันของคุณอาจสร้างตัวเลขสุ่มบางตัวด้วยตัวเอง
  • คุณอาจสมมติว่าอินพุตทั้งหมดนั้นถูกต้องโดยมีจำนวนหลักและตัวอักษรที่ถูกต้อง (ตัวระบุข้อความ 5 หลักอย่างน้อย 20 หลักสำหรับวลีสำคัญและอื่น ๆ ) คุณอาจคิดว่าสายอักขระของคุณ (ข้อความและคำหลัก) ได้ลบเครื่องหมายวรรคตอนและช่องว่างทั้งหมดแล้วยกเว้นสตริงที่คุณอนุญาตในรุ่นของคุณและหมายเลขนั้นถูกแบ่งเขตด้วยสัญลักษณ์ตัวเลขแล้ว
  • คำหลักแรกไม่ควรมีตัวอักษรซ้ำกันและในรหัสของคุณคุณอาจคิดว่ามันไม่มีตัวอักษรซ้ำกัน
  • ภาษาที่คุณใช้ในการเข้ารหัสไม่สำคัญตราบใดที่ภาษานั้นมีมาก่อนตัวอักษรจะมีอยู่ก่อนหน้าและคุณระบุภาษาที่คุณใช้ในคำตอบของคุณ
  • ไม่ว่าคุณจะใช้ตัวอักษรแบบใดสำหรับกระดานหมากรุกแบบคร่อมตัวคุณคุณสามารถเพิ่มหรือลบสัญลักษณ์เพื่อเอากระดานหมากรุกออกได้ ระบุสิ่งที่คุณใช้สัญลักษณ์เหล่านั้นสำหรับ (ตัวอย่างเช่นเครื่องหมายวรรคตอนสัญลักษณ์ "ข้อความเริ่มต้น" แยกต่างหากสัญลักษณ์สำหรับคำทั่วไป) คุณอาจนำหน้าหมายเลขทั้งหมดและสะกดตัวเลขหรือใส่ตัวเลขแต่ละหลักในกระดานหมากรุกโดยใช้ช่องที่มีสัญลักษณ์กำกับนั้นมีไว้เพื่อสิ่งอื่น โปรดระบุกระดานหมากรุกที่คุณใช้ในคำตอบของคุณ
  • เอาต์พุตควรเป็นสตริงของกลุ่มห้าหลักที่คั่นด้วยช่องว่างรายการของจำนวนเต็มห้าหลักหรือสิ่งที่คล้ายกัน
  • ฉันใช้การจัดทำดัชนีเป็นศูนย์และ0123456789ในตัวอย่างของฉัน คุณอาจใช้การจัดทำดัชนี 1 แบบ1234567890หรือระบบอื่นในคำตอบตราบใดที่คุณระบุสิ่งที่คุณใช้

นี่คือตัวอย่างการใช้งานบน IdeoneIdeone

นี่คือโพสต์ที่ยาวนานและฉันเขียนส่วนใหญ่ด้วยมือดังนั้นหากมีชิ้นส่วนที่สับสนในโพสต์นี้หรือข้อผิดพลาดในการนับและการย้ายโปรดแจ้งให้เราทราบ ขอให้โชคดีและการเล่นกอล์ฟที่ดี!


1
adding the first two digits without addingคุณหมายถึงการถือครอง?
isaacg

@isaacg ใช่ฉันทำ แก้ไข
Sherlock9

คุณช่วยอธิบายเกี่ยวกับสิ่งที่คุณหมายถึงwithout borrowingและwithout carrying? คุณหมายถึงการเพิ่มและลบตัวดัดแปลง10เช่น(6+7) mod 10 = 3และ(6-8) mod 10 = 8?
R. Kap

@ R.Kap ใช่ให้ฉันไปอธิบายว่า
Sherlock9

เราจำเป็นต้องแบ่งเขตตัวเลขหรือไม่
R. Kap

คำตอบ:


10

Python 3 , 1423 1348 1324 1316 1300 1286 1250 1249 1209 1206 1204 1204 ไบต์

นี่เป็นสนามกอล์ฟที่ยาวที่สุดที่ฉันเคยเล่นมาและเป็นสนามกอล์ฟเดียวที่ฉันกังวลอย่างมากเกี่ยวกับชื่อตัวแปรที่มีตัวอักษรเดียว ยินดีต้อนรับคำแนะนำการเล่นกอล์ฟ ลองออนไลน์!

ฉันเข้ารหัสด้วยตัวอักษรละตินตัวพิมพ์ใหญ่กับตัวละครที่เพิ่มขึ้น.และ#การใช้ 0 การจัดทำดัชนีและ0123456789เมื่อมีการแปลงไปg tกระดานหมากรุกของฉันอยู่ในรูปแบบที่คล้ายกับตัวอย่างต่อไปนี้:

  2 9 7 4 5 8 3 1 0 6    # C
  S E N A T O R I        # keyword
0 B D G J L P U W Y .    # remaining alphabet arranged in columns
6 C F H K M Q V X Z #    # . and # at the end

แก้ไข: -63 ไบต์ขอบคุณที่ข้อเสนอแนะของ TuukkaX เพื่อย่อฟังก์ชั่นที่ใช้บ่อยบางตัวด้วยตัวแปรตัวอักษรหนึ่งตัว -12 ไบต์จากการสร้างa, g, tกะทัดรัดยิ่งขึ้น

แก้ไข: -24 ไบต์จากการสร้างโดยลบชื่อตัวแปรสำหรับคีย์กลางที่ใช้เพียงครั้งเดียวคือa, g, s, S, k, Kไบต์จากการทำโดยการเอาชื่อตัวแปรสำหรับคีย์กลางที่มีการใช้เพียงครั้งเดียวคือ

แก้ไข: -74 ไบต์จากการรวบรวมH(), T() and C()ไบต์จากการรวม

แก้ไข: -1 ไบต์ขอบคุณที่นิคสำหรับข้อเสนอแนะของพวกเขาเปลี่ยนไปord(s[i])+ord(s[i+1]) sum(map(ord,s[i:i+2]))-2 ไบต์จากการเปลี่ยน 2 โทรไป+=[a] +=a,-13 ไบต์จากการเปลี่ยนแปลงวิธีการที่พบดัชนีต่ำสุดของG() s-2 ไบต์จากการเปลี่ยนไปy=(y+1)%v y=-~y%v-15 ไบต์จากกำหนดที่จะk.index() K-4 ไบต์จากกำหนดที่จะ10 W-5 ไบต์จากกำหนด1-I(d[-1])ที่จะอยู่ภายในX V-3 ไบต์จากการเขียนC()ลูปหลัก -2 T()ไบต์จากจัดระเบียบ

I=int;L=list;E=len;R=range;B=str;J=''.join;W=10
def H(s,e):
 for i in R(e-E(s)):s+=chr(48+sum(map(ord,s[i:i+2]))%32%W)
 return s
def Q(s):
 r=[0]*E(s);s=L(s)
 for z in R(E(s)):b=s.index(min(s));r[b]=z;s[b]="~"
 return r
def T(x,k,d=0):
 u=E(x);v=E(k);g=R(v);K=k.index;n=u//v+1;w=[];e=r=y=0;i=K(y);c=[]
 if d:
  while r<n:
   if r>n-1:i=min(i,(u%v or v))
   w+=L(x[e:e+i]),;e+=i;i+=1;r+=1
   if i>v:y=-~y%v;i=K(y)
  r=y=0;i=v-K(y)
  while r<n:
   w[r]+=L(x[e:e+i]);e+=i;i-=1;r+=1
   if i<1:y+=1;i+=v-K(y);r+=1
  w[-1]+=['']*(v-E(w[-1]))
  for j in g:c+=J(z[j]for z in w),
 else:c=[x[i::v]for i in g]
 s=[0]*v
 for f in g:s[k[f]]=c[f]
 return J(s)
def C(m,s,w,n):
 t={".":s[-2:],"#":s[-1]*2};j=z=0
 for x in R(26):
  v=chr(x+65)
  if v in w:t[v]=s[w.index(v)]
  else:t[v]=s[z-2]+s[j];j+=z;z=-~z%2
 r=J(i.isdigit()and i or t[i]for i in m)
 return r+n[:-E(r)%5]
def V(m,w,P,d,A,M,n):X=1-I(d[-1]);t=J(B(Q(P[W:20])[I(J(B((I(H(J(B((I(M[i])-I(d[i]))%W)for i in R(5)),W)[i])+I(Q(P[:W])[i]))%W)for i in R(W))[i])])for i in R(W));u=H(t,60)[W:];p=A+I(u[-2]);v=T(u,Q(t));z=T(T(C(m,J(B(i)for i in Q(u[40:])),w,n),Q(v[:p])),Q(v[p:p+A+I(u[-1])]),1);e=[z[5*i:5*-~i]for i in R(-(-E(z)//5))];return' '.join(e[:X]+[M]+e[X:])

Ungolfing:

def chain_add(seq, end):
    for i in range(end - len(seq)):
        seq += chr(48+sum(map(ord,seq[i:i+2]))%32%10)
    return seq

def sequent(seq):
    res = [0]*len(seq)
    seq = list(seq)
    for z in range(len(seq)):
        b = seq.index(min(seq))
        res[b] = z
        seq[b] = "~"
    return res

def transpose(text, keys, disrupt=False):
    if disrupt:
        num_rows = len(text) // len(keys) + 1
        len_last = len(text) % len(keys)
        if len_last == 0:
            len_last = len(keys)
        d_rows = []
        text_index = 0
        current_row = 0
        stop_key = 0
        stop_index = keys.index(stop_key)
        while current_row < num_rows:
            if current_row > num_rows-1:
                stop_index = min(stop_index, len_last)
            d_rows += [list(text[text_index:text_index+stop_index])]
            text_index += stop_index
            stop_index += 1
            if stop_index>len(keys):
                stop_key = (stop_key+1) % len(keys)
                stop_index = keys.index(stop_key)
            current_row += 1
        current_row = 0
        stop_key = 0
        stop_len = len(keys) - keys.index(stop_key)
        while current_row < num_rows:
            d_rows[current_row] += list(text[text_index:text_index+stop_len])
            text_index += stop_len
            stop_len -= 1
            if stop_len < 1:
                stop_key += 1
                stop_len = len(keys) - keys.index(stop_key)
                current_row += 1
            current_row += 1
        d_rows[-1] += ['']*(len(keys)-len(d_rows[-1]))
        columns = []
        for j in range(len(keys)):
            columns += [''.join(i[j]for i in d_rows)]
    else:
        columns = ['']*len(keys)
        for t in range(len(text)):
            columns[t%len(keys)] += text[t]
    res = [0]*len(keys)
    for index in range(len(keys)):
        res[keys[index]] = columns[index]
    return''.join(res)

def checkerboard(message, seq, word, null):
    trans = {".":seq[-2:], "#":seq[-1]*2};res='';j=z=0
    for x in range(26):
        v = chr(x + 65)
        if v in word:
            trans[v] = seq[word.index(v)]
        else:
            trans[v] = seq[z-2] + seq[j]
            j += z
            z = (z+1) % 2
    for i in message:
        if i.isdigit():
            res += i
        else:
            res += trans[i]
    return res + null[:-len(res)%5]

def vic_cipher(message, keyword, phrase, date, agent, m_id, null):
    s1 = sequent(phrase[:10])
    s2 = sequent(phrase[10:20])
    a = ''.join(str((int(m_id[i])-int(date[i]))%10) for i in range(5))
    g = ''.join(str((int(a[i])+int(s1[i]))%10) for i in range(10))
    t = ''.join(str(s2[int(g[i])]) for i in range(10))
    u = chain_add(t,60)[10:]
    p = agent+int(u[-2])
    q = agent+int(u[-1])
    seqT = sequent(t)
    v = transpose(u,seqT)
    k1 = sequent(v[:p])
    k2 = sequent(v[p:p+q])
    c = ''.join(str(i)for i in sequent(u[40:]))
    x = checkerboard(message,c,keyword,null)
    y = transpose(x,k1)
    z = transpose(y,k2,1)
    e = [z[5*i:5*(i+1)] for i in range(-(-len(z)//5))]
    X = 1-int(date[-1])
    return ' '.join(e[:X] + [m_id] + e[X:])

2
Python 3 อนุญาตให้ใช้อักขระ Unicode เป็นตัวแปร FYI
พอล

เปลี่ยนord(seq[i])+ord(seq[i+1])เป็นsum(map(ord,seq[i:i+2]))บันทึก 1 ตัวที่ฉันเชื่อ

3

C, 2880 2769 2766 2762 2743 2741 2739 2799 2699 2458 ไบต์

#include<stdio.h>
#define m(x)malloc(x)
#define Y(x)strlen(x)
typedef int i;typedef char*c;c _(c A,i B,i D){if(D>=B){return A;}c C=m(Y(A)+2);sprintf(C,"%s%c",A,48+(A[D]+A[D+1]-96)%10);return _(C,B,D+1);}c l(c A){i J=Y(A);c P=m(J+2);for(i m=0;m<J;m++){P[m]=32;}for(i v=0;v<J;v++){char G;i R;for(i u=0;u<J;u++){R=u<1|A[u]<G?u:R;G=u<1|A[u]<G?A[u]:G;}P[R]=48+v;c V=m(J);for(i t=0;t<J;t++){V[t]=t!=R?A[t]:97;}A=V;}return P;}c S(c C,c N,c I,char U){srand(time(NULL));i M=Y(I);i O=Y(N);i R=rand()%M;c Q=m(M+1);for(i u=R;u<M;u++){Q[u-R]=I[u];}Q[M-R]=46;for(i H=0;H<R;H++){Q[H+M-R+1]=I[H];}c g=m(28);c V=m(28);strcat(V,C);sprintf(g,"%s%s",N,"BCDFGHJKLMPQUVWXYZ.#");i B=Y(N);for(i q=B;q<10;q++){for(i x=0;x<10;x++){char J[2]={C[q],C[x]};V[B]=48+atoi(J);B++;}}c w=m(M*2+4);for(i J=0;J<=M;J++){i K=0;for(i X=0;X<28;X++){if(Q[J]==g[X]){char F[3];sprintf(F,"%d",V[X]-48);strcat(w,F);K=1;}}if(K<1){w[Y(w)]=Q[J];}}i f=Y(w);if(f%5>0){c P=m(5-f%5);for(i E=0;E<5-f%5;E++){P[E]=U;}strcat(w,P);}return w;}c a(c I,c U){i M=Y(I),K=Y(U);c T=m(M);i F=0;for(i b=0;b<K;b++){for(i y=0;y<K;y++){if(U[y]==48+b){for(i u=y;u<M;u+=K){T[F]=I[u];F++;}}}}return T;}c da(c I,c K){i e=Y(I),k=Y(K);c T=m(e);for(i y=0;y<e;y++){T[y]=32;}i F,P;F=P=0;for(i u=0;u<k;u++){for(i v=0;v<k;v++){T[F]=I[P];P++;F++;if(K[v+1]-48==u){for(i C=1;C<k-v;C++){F+=k-v-C;for(i E=0;E<=v+C;E++){if(F<e&P<e){T[F]=I[P];}F++;P++;}}break;}}if(F>e){break;}}i U=0;for(i g=0;g<e;g++){U=T[g]-48<10&-1<T[g]-48?U+1:U;}for(i j=U;j<e;j++){for(i x=0;x<e;x++){if(T[x]==32){T[x]=I[j];break;}}}return a(T,K);}En(c n,c m,c k,i d,c v,c s,char u){c S1,S2;S1=m(10);S2=m(10);for(i i=0;i<20;i++){if(i<10){S1[i]=k[i];}else{S2[i-10]=k[i];}}S1=l(S1);S2=l(S2);c M=m(5);for(i i=4;i>-1;i--){M[i]=48+(s[i]-v[i])%10;}c G=_(M,5,0);for(i y=0;y<10;y++){G[y]=48+(S1[y]+G[y]-96)%10;}c N="0123456789";c T=m(10);for(i q=0;q<10;q++){for(i t=0;t<10;t++){if(N[t]==G[q]){T[q]=S2[t];}}}c Z=_(T,50,0);c U=m(50);for(i h=0;h<50;h++){U[h]=Z[h+10];}i p,q;for(i b=49;b>10;b++){if(U[b]!=U[b-1]){q=d+U[b]-48;p=d+U[b-1]-48;break;}}c V=m(50);i Ct=0;for(i j=0;j<10;j++){for(i o=0;o<10;o++){if(l(T)[o]==48+j){for(i x=o;x<o+41;x+=10){V[Ct]=U[x];Ct+=1;}}}}c K1=m(p);c K2=m(q);for(i D=0;D<p+q;D++){if(D<p){K1[D]=V[D];}else{K2[D-p]=V[D];}}K1=l(K1);K2=l(K2);c C=m(10);for(i b=40;b<50;b++){C[b-40]=U[b];}C=l(C);c t=da(a(S(C,m,n,u),K1),K2);i O=0;for(i B=0;B<Y(t)/5+1;B++){if(B==Y(t)/5-v[Y(v)-1]+49){printf("%s ",s);}else{for(i J=O;J<O+5;J++){printf("%c",t[J]);}printf(" ");O+=5;}}}

เอ้ยฉัน นี่เป็นรายการที่ยาวที่สุดที่ฉันเคยเล่นกอล์ฟ นี่เป็นครั้งแรกที่ฉันใช้ชื่อตัวแปรแบบอักขระเดียวสำหรับขอบเขตทั่วโลกและต้องย้ายไปใช้อักขระสองสามตัว (ความจริงที่ว่าฉันไม่สามารถประกาศตัวแปรไม่ได้ช่วยไม่ได้) เคล็ดลับการเล่นกอล์ฟมีความนิยมอย่างมาก

Ungolfed

รวบรวมโดยไม่มีคำเตือนใด ๆ ซึ่งแตกต่างจากรุ่น golfed การเปลี่ยนแปลงเล็กน้อยที่เกิดขึ้นกับเวอร์ชั่นของกอล์ฟจะไม่ปรากฏในเวอร์ชั่นที่ไม่ดีนี้

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>

char*Chain_Add(char*String,int End,int Start){
  if(Start>=End){return String;}
  char*C=malloc(strlen(String)+2);
  sprintf(C,"%s%c",String,'0'+(((String[Start]-'0')+(String[Start+1]-'0'))%10));
  return Chain_Add(C,End,Start+1);
}

char*Sequent(char*String){
  int J=strlen(String);
  char*P=malloc(J+2);
  for(int m=0;m<J;m++){
    P[m]=' ';
  }
  for(int v=0;v<J;v++){
    char G;
    int R;
    for(int u=0;u<J;u++){
      R=(u<1||String[u]<G)?u:R;
      G=(u<1||String[u]<G)?String[u]:G;
    }
    P[R]='0'+v;
    char*V=malloc(J);
    for(int t=0;t<J;t++){
      if(t!=R){
    V[t]=String[t];
      }
      else{
    V[t]='a';
      }
    }
    String=V;
  }
  return P;
}

char*Straddling_Checkerboard(char*C,char*Key,char*Message,char null){
  srand(time(NULL));
  int Msg_Len=strlen(Message);
  int Key_Len=strlen(Key);
  int R=rand()%Msg_Len;
  char*Q=malloc(Msg_Len+1);
  for(int u=R;u<Msg_Len;u++){
    Q[u-R]=Message[u];
  }
  Q[Msg_Len-R]='.';
  for(int H=0;H<R;H++){
    Q[H+Msg_Len-R+1]=Message[H];
  }
  char*Alphabet=malloc(26);
  for(int W=0;W<26;W++){
    Alphabet[W]='A'+W;
  }
  int q=0;
  char*e=malloc(Key_Len);
  for(int z=0;z<Key_Len;z++){
    if(strchr(e,Key[z])!=NULL){
      q++;
    }
    else{
      e[z-q]=Key[z];
    }
  }
  int r=0;
  for(int h=0;h<26;h++){
    if(strchr(e,Alphabet[h-r])!=NULL){
      for(int X=h-r;X<26;X++){
    Alphabet[X]=Alphabet[X+1];
      }
      r++;
    }
  }
  char*Checkerboard=malloc(28);
  for(int i=0;i<26;i++){
    if(i<strlen(e)){
      Checkerboard[i]=e[i];
    }
    else{
      Checkerboard[i]=Alphabet[i-strlen(e)];
    }
  }
  Checkerboard[26]='.';
  Checkerboard[27]='#';
  char*Values=malloc(28);
  strcat(Values,C);
  int B=strlen(e);
  for(int q=B;q<10;q++){
    for(int x=0;x<10;x++){
      char J[2]={C[q],C[x]};
      Values[B]='0'+atoi(J);
      B++;
    }
  }
  char*Encoded=malloc(Msg_Len*2+4);
  for(int J=0;J<=Msg_Len;J++){
    int K=0;
    for(int X=0;X<28;X++){
      if(Q[J]==Checkerboard[X]){
    char F[3];
    sprintf(F,"%d",Values[X]-'0');
    strcat(Encoded,F);
    //printf("F = %s while Q[J] = %c and Checkerboard[X] = %c and Encoded = %s\n",F,Q[J],Checkerboard[X],Encoded);
    K=1;
      } 
    }
    if(K<1){
      Encoded[strlen(Encoded)]=Q[J];
    }
  }
  int Encded_Len=strlen(Encoded);
  if(Encded_Len%5>0){
    char*P=malloc(5-Encded_Len%5);
    for(int E=0;E<5-Encded_Len%5;E++){
      P[E]=null;
    }
  strcat(Encoded,P);
  }
  return Encoded;
}

char*Transpose(char*Message,char*K1){
  int Msg_Len=strlen(Message),K1_Len=strlen(K1);
  char*T=malloc(Msg_Len);
  int F=0;
  for(int i=0;i<K1_Len;i++){
    for(int y=0;y<K1_Len;y++){
      if(K1[y]=='0'+i){
    for(int u=y;u<Msg_Len;u+=K1_Len){
      T[F]=Message[u];
      F++;
    }
      }
    }
  }
  return T;
}

char*Disrupted_Transpose(char*Message,char*K2){
  int Msg_Len=strlen(Message),K2_Len=strlen(K2);
  char*T=malloc(Msg_Len);
  for(int y=0;y<Msg_Len;y++){
    T[y]=' ';
  }
  int F=0;
  int P=0;
  for(int u=0;u<K2_Len;u++){
    for(int v=0;v<K2_Len;v++){
      T[F]=Message[P];
      P++;F++;
      if(K2[v+1]-'0'==u){
        for(int C=1;C<K2_Len-v;C++){
      F+=K2_Len-v-C;
      for(int E=0;E<=v+C;E++){
        if(F<Msg_Len&P<Msg_Len){
          T[F]=Message[P];
        }
        F++;P++;
      }
    }
    break;
      }
    }
    if(F>Msg_Len){
      break;
    }
  }
  int U=0;
  for(int g=0;g<Msg_Len;g++){
    U=(T[g]-'0'<10&-1<T[g]-'0')?U+1:U;
  }
  for(int j=U;j<Msg_Len;j++){
    for(int x=0;x<Msg_Len;x++){
      if(T[x]==' '){
    T[x]=Message[j];
    break;
      }
    }
  }
  return Transpose(T,K2);
}

void VIC_Encoder(char*Message,char*Phrase,char*Key,int a_id,char*date,char*m_id,char null){
  char*S1=malloc(10);
  char*S2=malloc(10);
  for(int i=0;i<20;i++){
    if(i<10){
      S1[i]=Key[i];
    }
    else{
      S2[i-10]=Key[i];
    }
  }
  S1=Sequent(S1);
  S2=Sequent(S2);
  char*M=malloc(5);
  for(int i=4;i>-1;i--){
    M[i]='0'+(((m_id[i]-'0')-(date[i]-'0'))%10);
  }
  char*G=Chain_Add(M,5,0);
  for(int y=0;y<10;y++){
    G[y]='0'+(((S1[y]-'0')+(G[y]-'0'))%10);
  }
  char*N="0123456789";
  char*T=malloc(10);
  for(int q=0;q<10;q++){
    for(int t=0;t<10;t++){
      if(N[t]==G[q]){
    T[q]=S2[t];
      }
    }
  }
  char*Z=Chain_Add(T,50,0);
  char*U=malloc(50);
  for(int h=0;h<50;h++){
    U[h]=Z[h+10];
  }
  int p,q;
  for(int b=49;b>10;b++){
    if(U[b]!=U[b-1]){
      q=a_id+(U[b]-'0');
      p=a_id+(U[b-1]-'0');
      break;
    }
  }
  char*seqT=Sequent(T);
  char*V=malloc(50);
  int Count=0;
  for(int j=0;j<10;j++){
    for(int o=0;o<10;o++){
      if(seqT[o]=='0'+j){
    for(int x=o;x<o+41;x+=10){
      V[Count]=U[x];
      Count+=1;
    }
      }
    }
  }
  char*K1=malloc(p);
  char*K2=malloc(q);
  for(int D=0;D<p+q;D++){
    if(D<p){
      K1[D]=V[D];
    }
    else{
      K2[D-p]=V[D];
    }
  }
  K1=Sequent(K1);
  K2=Sequent(K2);
  char*C=malloc(10);
  for(int b=40;b<50;b++){
    C[b-40]=U[b];
  }
  C=Sequent(C);
  char*Transposed_2=Disrupted_Transpose(Transpose(Straddling_Checkerboard(C,Phrase,Message,null),K1),K2);
  int O=0;
  for(int B=0;B<strlen(Transposed_2)/5+1;B++){
    if(B==strlen(Transposed_2)/5-date[strlen(date)-1]+'1'){
      printf("%s ",m_id);
    }
    else{
      for(int J=O;J<O+5;J++){
    printf("%c",Transposed_2[J]);
      }
      printf(" ");
      O+=5;
    }
  }
}

หมายเหตุ

  • ใช้กระดานหมากรุกคล้ายกับข้อความต่อไปนี้ในการเข้ารหัสข้อความ:

      3 4 5 6 2 3 4 5 6 7
      S E N A T O R I     
    6 B C D F G H J K L M 
    7 P Q U V W X Y Z . #
    
  • นี่จะถือว่าสตริงที่เกี่ยวข้องทั้งหมดถูกกำหนดเป็นตัวพิมพ์ใหญ่ ข้อความควรมีเครื่องหมายวรรคตอนทั้งหมดยกเว้นช่วงเวลาที่ลบออกและตัวเลขทั้งหมดแบ่งเขตโดย#s ในขณะที่วลีสำคัญควรมีการเว้นวรรคตอนทั้งหมดออก

  • ข้อความที่เข้ารหัสผลลัพธ์ถูกส่งออกไปยัง STDOUT เป็นสตริงของกลุ่มห้าหลักที่คั่นด้วยช่องว่าง

  • ข้อความอินพุตควรเป็นภาษาอังกฤษ

  • ฉันจะรวมฟังก์ชั่นบางอย่างที่ฉันใช้ แต่แล้วฉันจะต้องใช้ชื่อตัวแปรสองตัวอักษรเพิ่มเติมทำให้โปรแกรมสุดท้ายยาวกว่ามันจะมีฟังก์ชั่นอีกไม่กี่ตัว

  • ในปัจจุบันนี้ไม่ได้สันนิษฐานว่าคำหลัก (อย่างน้อยเป็นภาษาอังกฤษ) จะมีชุดของตัวอักษรเดียวกันอยู่เสมอและประกอบไปด้วยการลบรายการที่ซ้ำกันจัดการกระดานหมากรุก ฯลฯ ความสามารถนี้ไม่จำเป็นต้องใช้โดย OP, ตอนนี้ฉันกำลังเล่นกอล์ฟที่ไม่จำเป็นต้องใช้ไบต์ที่ไม่จำเป็น อัปเดตสำหรับรุ่น golfed


2

JavaScript (ES6), 946 938 953 ไบต์

V=(c,d,f,g,j,k,m)=>{S=a=>a.split``,J=a=>a.join``,A=(a,b)=>{for(i=0;a[L="length"]<b;a+=(a[i++]- -a[i])%h);return a},Q=b=>(a=S(b).sort(),S(b).map(b=>a[i=a[X="indexOf"](b)]=i)),u=A(t=J(S(A(J(S(k).map((a,b)=>Math.abs(a-g[b]))),h=10)).map((a,b)=>Q(f[C="slice"](h,20))[(Q(f[C](0,h))[b]- -a)%h])),60)[C](h),T=((a,b,c)=>{if(r=Array(l=b[L]).fill(""),c){for(e=a[L]/l,i=0,w=[],u=R=b[X](x=0);i<e;)w[i++]=a[P](0,R++),u?u=0:R>l||(R=b[X](u=++x));for(i=0;i<e;)w[i]=J(w[i].concat(a[P](0,l-w[i++][L])));a=J(w)}for(i in a)r[+b[i%l]]+=a[i];return r}),v=J(T(u,Q(t))),q=J(Q(u[C](-h))),t="ABCDEFGHIJKLMNOPQRSTUVWXYZ#".match(new RegExp("[^"+d+"]","g")),t[P="splice"](9,0,"."),M=[];for(i in t)M[t[i]]=q[8^i/h]+(M[d[i]]=q[i%h]);for(n=c[L],b=J((c[C](n-=new Date%n)+"."+c[C](0,n)).split(/ |/).map(a=>M[a]||a)),b+=m.repeat(5-b[L]%5),i=f=q=49;f==q;)f=+u[i-1]+j,q=+u[i++]+j;return t=J(T(S(J(T(b,Q(v[C](0,f))))),Q(v.substr(f,q)),1)).match(/.{5}/g),g=-g[C](-1),g++&&t[P](g||t[L],0,k),t}

ฉันเห็นในช่วงสุดสัปดาห์นี้ยังไม่มีรายการ JS สำหรับเรื่องนี้ดังนั้นนี่คือความพยายาม (นาทีสุดท้าย) ของฉัน การนำไปใช้งานและเล่นกอล์ฟสิ่งนี้มันช่างบ้าคลั่งอย่างมาก!

ตัวอย่างการสาธิต

แก้ไข: -8 ไบต์

รับรู้มีวงเล็บพิเศษรอบฟังก์ชั่น S,J,A,Q

แก้ไข: +15 ไบต์

อัปเดตตรรกะสำหรับวิธีการmessage idวางในข้อความสุดท้าย (ขณะนี้มีการจัดทำดัชนี 1 รายการและ 0 ไม่รวมอยู่ในผลลัพธ์)

Ungolfed

chainAdd = (s,l)=>{for(i=0;s.length<l;s+=(s[i++]- -s[i])%10);return s;}

sequentialize = (s)=> {
    a=s.split('').sort();
    return s.split('').map(c=>(i=a.indexOf(c),a[i]='',i));  
}

transpose = (s,k,disruptive)=>{
    var result=Array(k.length).fill('')
    if(disruptive){
        rows=[]
        k_index=0;
        rowLength=k.indexOf(k_index);
        triangling=!rowLength;

        expectedRows = s.length/k.length
        for(row=0;row<expectedRows;row++){
            rows[row]=s.splice(0,rowLength++)
            if(triangling){     
                if(rowLength>k.length){
                    triangling=false;
                    rowLength=k.indexOf(++k_index)              
                }
            }
            else{               
                triangling=true;
            }
        }

        for(row=0;row<expectedRows;row++){
            rows[row]= rows[row].concat(s.splice(0,k.length-rows[row].length)).join('')
        }
        s=rows.join('')
    }
    for(i in s)
        result[+k[i%k.length]]+=s[i];   
    return result;
}

checkerboard =(message,seq, keyword, nulls)=>{  
    t='ABCDEFGHIJKLMNOPQRSTUVWXYZ#'.match(new RegExp('[^'+keyword+']','g'));
    t.splice(9,0,'.')

    map=[]
    for(i in t)
        map[t[i]]=(seq[8^(i/10)])+(map[keyword[i]]=seq[i%10])

    r = new Date%message.length;
    rotateMessage=message.substr(message.length-r)+'.'+message.substr(0,message.length-r)

    result =rotateMessage.split(/ |/).map(x=>map[x]||x).join('');
    result+=nulls.repeat(5-result.length%5)

    return result;
}

vic = (message, keyword, phrase, date, agent, m_id, nulls)=>{
    s1=sequentialize(phrase.substr(0,10))//.join('')
    s2=sequentialize(phrase.substr(10,10))//.join('')

    r = m_id.split('').map((x,i)=>Math.abs(x-date[i])).join('')
    g = chainAdd(r,10).split('').map((x,i)=>(s1[i]- -x)%10);

    t = g.map(i=>s2[+i]).join('');
    u=chainAdd(t,60).substr(10)

    var p,q;
    for(i=49;p==q;i++){
        p=agent + +u[i-1];
        q=agent + +u[i];
    }
    seqT = sequentialize(t);
    v=transpose(u,seqT).join('');

    k1 = sequentialize(v.substr(0,p));
    k2 = sequentialize(v.substr(p,q));
    c  = sequentialize(u.substr(-10)).join('')

    CB =checkerboard(message,c, keyword, nulls);
    t1=transpose(CB,k1).join('')
    t2=transpose(t1.split(''),k2,1).join('').match(/.{5}/g);
    (d=-date.substr(-1))&&t2.splice((d+1)||t2.length,0,m_id);
    return t2;
}

หมายเหตุ

  • ใช้กระดานหมากรุกคล้ายกับข้อความต่อไปนี้ในการเข้ารหัสข้อความ:

      3 1 0 5 9 6 8 7 2 4
      S E N A T O R I
    2 B C D F G H J K L .
    4 M P Q U V W X Y Z #
    
  • สตริงทั้งหมดจะได้รับเป็นตัวพิมพ์ใหญ่ ข้อความนั้นเป็นตัวอักษรและตัวเลขละติน (บวก.และ#) และควรลบเครื่องหมายวรรคตอนทั้งหมด (ยกเว้นจุด) ตัวเลขทั้งหมดควรถูกทำเครื่องหมายด้วย#s วลีสำคัญควรลบเครื่องหมายวรรคตอน / ช่องว่างออกทั้งหมด

  • ข้อความผลลัพธ์ถูกส่งคืนเป็นอาร์เรย์ของสตริง 5 หลัก

การเพิ่มประสิทธิภาพ

  • ฉันรู้สึกว่ามีวิธีที่จะใช้ "ทุกภาษา" เพื่อประหยัดไบต์บางส่วน ถ้าฉันมีเวลามากกว่านี้ฉันจะตั้งค่าใหม่ให้ถือว่าภาษาเป็นแบบฮาวายที่มีตัวอักษรเพียง 12 ตัว

  • คำแนะนำการเล่นกอล์ฟใด ๆ ยินดีต้อนรับเสมอ


คุณกรุณาเพิ่มตัวอย่างเพื่อให้ฉันสามารถตรวจสอบว่ามันทำงาน ถ้าเป็นเช่นนั้นฉันสามารถมอบรางวัลให้คุณได้
R. Kap

@ R.Kap แน่นอนว่าฉันได้เพิ่มตัวอย่างข้อมูล
SLuck49

อืม ... ในการสาธิตที่message identifierดูเหมือนจะห่างจากปลายแทน7 6นอกจากนี้ในเวอร์ชั่นที่ไม่ได้รับการแต่งแต้มของคุณIdดูเหมือนว่าจะอยู่6ห่างจากจุดเริ่มต้นแทนที่จะจบ
R. Kap

@ R.Kap ใช่มีข้อผิดพลาดเมื่อฉันโพสต์มันครั้งแรก (จะต้องไม่แก้ไขใน ungolfed) สำหรับนักกอล์ฟฉันคิดว่ามันเป็นดัชนี 0 เพราะถ้า1อย่างนั้นถ้า อย่างนั้นคุณจะบอกว่าmessage identifierควรจะทำ0อะไรต่อไป? ฉันสามารถเปลี่ยนได้ฉันแค่ต้องรู้
SLuck49

ฉันจะบอกว่าใน0การmessage identifierควรละเว้นจากการส่งออก
R. Kap

1

Clojure, 1197 1212 ไบต์

อืมฉันเหนื่อยแล้ว

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

(defn enc[I K E D Y M](let[P split-at A concat Z zipmap R partition W mapcat % count X repeat O vector / map x(fn[C](apply / O C))G range t 10 r(G t)m(fn[i](mod i t))F(fn[[n & N]](/ last(iterate(fn[[[b & N]a]][(A N[(m(+ a b))])b])[N n])))Q(fn[S](for[i(G(% S))a[(nth S i)]](apply +(%(filter #{a}(take i S)))(for[b S :when(pos?(compare a b))]1))))[S J](/ Q(P t(take 20 E)))T(/(Z r J)(/ m(/ + S(F(/ - M D)))))U(take 50(drop t(F T)))l(last U)p(+ Y(last(remove #{l}U)))V(W(Z(Q T)(x(R t U)))r)[k j](/ Q(P p(take(+ p Y l)V)))B(into(Z(/ char(G 48 58))(G))(/(fn[i c][c(+(*(quot i 10)20)(nth(Q(reverse(take t(reverse U))))(m i)))])(G)(A(str K",,")(remove(set K)(/ char(A(G 65 91)".#"))))))?(% k)T(vec(filter some?(W(Z k(x(R ?(A(flatten(R 5(A(W str(/ B(let[[b e](P(rand-int(count I))I)](apply str(A e".. "b)))))(X 4(B\,)))))(X(dec ?)nil)))))(G ?))))w (% j)NR(+(quot(% T)w)1)L(flatten(for[k r](for[i(G(.indexOf j k)(inc w))](G i))))C(for[[r c](/ O(rest(reductions + -1(/(fn[i](get{0 1}i 0))L)))L):when(< r NR)][r c])H(R 5(filter some?(W(Z j(x(R w (A(vals(into(sorted-map)(/ O(A C(for[i(G NR)j(G w)c[[i j]]:when(not((set C)c))]c))T)))(X(dec w)nil)))))(G w))))](/(fn[p](apply str p))(let[[b e](P(-(% H)(D 6)-1)H)](A b[M]e)))))

อินพุตตัวอย่างและกรณีทดสอบ:

(def mymsg (clojure.string/upper-case "We are discovered. Take what you can. Burn everything else. Move to Safehouse Foxtrot#3#"))
(def mykey "SENATORI")
(def mypharase (clojure.string/upper-case (apply str (remove #{\space} "The first principle is that you must not fool yourself — and you are the easiest person to fool."))))
(def mydate [3 1 7 2 0 1 6])
(def mynum 9)
(def M [4 7 9 2 1])

;("61231" "12824" "71192" "58609" "92185" "48612" "14927" "22944" "34046" "13348" "04159" "38645" "70546" "20254" "22026" "64584" "21904" "47921" "90253" "42694" "42221" "56644" "14541")
(enc mymsg mykey mypharase mydate mynum M)

Ungolfed:

(defn enc[mymsg mykey mypharase mydate mynum M]
  (let[t       10
       r       (range t)
       m       (fn[i](mod i t))
       lagfib  (fn[[n & N]](map last(iterate(fn[[[b & N]a]][(concat N[(m(+ a b))])b])[N n])))
       toseq   (fn[S](for[i(range(count S))a[(nth S i)]](apply +(count(filter #{a}(take i S)))(for[b S :when(pos?(compare a b))]1))))
       [S1 S2] (map toseq(split-at t(take 20 mypharase)))
       M2      (take t(lagfib(map - M mydate)))
       G       (map m(map + S1 M2))
       Gmap    (zipmap r S2)
       T       (map Gmap G)
       U       (take 50(drop t(lagfib T)))
       L2      (last U)
       L1      (last(remove #{L2}U))
       p       (+ mynum L1)
       q       (+ mynum L2)
       seqT    (toseq T)
       V       (mapcat(zipmap seqT(apply map vector(partition t U)))r)
       [K1 K2] (map toseq(split-at p(take(+ p q)V)))
       C       (toseq(reverse(take t(reverse U))))
       B       (into(zipmap(map char(range 48 58))(range))(map(fn[i c][c(+(*(quot i 10)20)(nth C(m i)))])(range)(concat(str mykey",,")(remove(set mykey)(map char(concat(range 65 91)".#"))))))
      ;B       (into(zipmap(map char(range 48 58))(range))(map(fn[i c][c(+(nth C(quot i 3))(*(mod i 3)20))])(range)(flatten(apply map vector(partition 10(apply concat mykey",,"(apply map vector (partition 2(remove(set mykey)(map char(concat(range 65 91)".#")))))))))))
       N1      (count K1)
       mymsg   (flatten(partition 5(concat(mapcat str(map B(let[[b e](split-at 49 mymsg)](apply str(concat e".. "b)))))(repeat 4(B\,)))))
       T1      (vec(filter some?(mapcat(zipmap K1(apply map vector(partition N1(concat mymsg(repeat(dec N1)nil)))))(range N1))))
       N2      (count K2)
       NR      (+(quot(count T1)N2)1)
       cols    (flatten(for[k r](for[i(range(.indexOf K2 k)(+(count K2)1))](range i))))
       rows    (rest(reductions + -1(map(fn[i](get{0 1}i 0))cols)))
       coords  (for[[r c](map vector rows cols):when(< r NR)][r c])
       coords  (concat coords(for[i(range NR)j(range N2)c[[i j]]:when(not((set coords)c))]c))
       T2      (partition 5(filter some?(mapcat(zipmap K2(apply map vector(partition N2(concat(vals(into(sorted-map)(map vector coords T1)))(repeat(dec N2)nil)))))(range N2))))]
    (map(fn[p](apply str p))(let[[b e](split-at(-(count T2)(mydate 6)-1)T2)](concat b[M]e)))))

มันมีการใช้งานทางเลือกในกระดานหมากรุกBซึ่งเป็นเช่นเดียวกับในการกำหนดงาน แต่การส่งจะใช้อีกอันหนึ่งซึ่งตัวอักษรที่ไม่ได้ใช้กรอกแถวที่ 2 ก่อนแล้วจึงแทนที่ตัวที่สามแทนที่จะเติมคอลัมน์ทีละคอลัมน์


ถือว่าการเขียนโซลูชัน Clojure แต่หัวของฉันระเบิดในขณะที่ฉันกำลังอ่านคำถาม ใช้เวลาเขียนนานแค่ไหน?
Carcigenicate

อาจจะ 3 ชั่วโมงในขณะที่ดู Youtube ที่ด้านข้าง สิ่งนี้เริ่มต้นได้ง่ายมาก แต่ฉันกำลังจะยอมแพ้เมื่อฉันต้องติดตั้ง "การขนย้ายที่ถูกรบกวน" ครั้งที่สอง ตอนนี้coordsจะถูกสร้างขึ้นสองครั้งแรกสร้างรูปร่างสามเหลี่ยมแล้วเติมพิกัดใด ๆ ที่ขาดหายไป นอกจากนี้ "การขยายความยาวของทวีคูณของ N" อาจมีวิธีการแก้ปัญหาที่หรูหรากว่าการต่อส่วนประกอบ N - 1 เข้าด้วยกันและการแบ่งพาร์ติชันตามความยาวของ N.
NikoNyrh

โอ้ฉันลืมที่จะเปลี่ยนจุดแยกรหัสที่(split-at 49 mymsg)49 รหัสควรเป็นสิ่งที่ต้องการ(rand-int(count mymsg))คำตอบที่ถูกต้องจะเป็นบิตมากกว่า 1200 ไบต์ zzz
NikoNyrh

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