ลูกบาศก์ข้อความ text


17

ครั้งล่าสุดที่คุณสร้างข้อความแต่ตอนนี้คุณสามารถสร้างข้อความลูกบาศก์ได้หรือไม่?

ความท้าทาย

กำหนดสตริงให้ส่งออกสตริงในรูปแบบของคิวบ์

คุณสามารถสันนิษฐานได้ว่าสตริงจะมี 2 ตัวอักษรขึ้นไปเสมอและจะมีอักขระ ASCII ที่พิมพ์ได้เท่านั้น

วิธีการสร้างคิวบ์ข้อความ

ทักษะ mspaint แย่มาก

กรณีทดสอบ

Input:
Test

Output:
   Test
  e  ss
 s  e e
tseT  T
s  e e
e  ss
Test

Input:
Hello, world!

Output:
            Hello, world!
           e           dd
          l           l l
         l           r  r
        o           o   o
       ,           w    w

     w           ,      ,
    o           o       o
   r           l        l
  l           l         l
 d           e          e
!dlrow ,olleH           H
d           e          e
l           l         l
r           l        l
o           o       o
w           ,      ,

,           w    w
o           o   o
l           r  r
l           l l
e           dd
Hello, world!

Input:
Hi

Output:
 Hi
iHH
Hi

การใช้งานอ้างอิงใน Python

text = raw_input("Enter a string: ")

print " " * (len(text) - 1) + text

spaces = len(text) - 2
_spaces = spaces

for i in range(1, len(text) - 2 + 1):
    print " " * spaces + text[i] + " " * _spaces + text[(i + 1) * -1] + " " * (_spaces - spaces) + text[(i + 1) * -1]
    spaces -= 1

print text[::-1] + " " * _spaces + text[0]

spaces = _spaces - 1

for i in range(1, len(text) - 2 + 1):
    print text[(i + 1) * -1] + " " * _spaces + text[i] + " " * spaces + text[i]
    spaces -= 1

print text

กฎระเบียบ

  • นี่คือดังนั้นคำตอบที่สั้นที่สุดในจำนวนไบต์ชนะ! Tiebreaker ถูกอัปเดตมากที่สุด
  • ช่องโหว่มาตรฐานไม่ได้รับอนุญาต
  • อนุญาตการขึ้นบรรทัดใหม่และการเว้นวรรคต่อท้าย

อนุญาตให้ใช้ช่องว่างต่อท้ายได้หรือไม่
Neil

@ Neil ใช่ (15 ตัวอักษร)
acrolith

แค่อยากรู้อยากเห็นตัวละครเพิ่มเติมในชื่อเรื่องท้าทายคืออะไร?
AdmBorkBork

@ TimmyD "คิวบ์ข้อความ" มีความยาว 14 ตัวอักษรหัวเรื่องต้องมีความยาวอย่างน้อย 15 ตัวอักษรดังนั้นฉันจึงเพิ่มจุดเล็ก ๆ ฉันคิดว่ามันเป็นสิ่งนี้
acrolith

อาโอเค. มันแสดงให้เห็นว่าเป็นวงกลมขนาดใหญ่กว่ามากใน IE บนคอมพิวเตอร์ของฉันดังนั้นคำถามของฉัน
AdmBorkBork

คำตอบ:



4

Python 2, 228 223 221 203 199 195 189

t=input()
x=" "
l=len(t)-1
q=l-1
f=range(q,0,-1)
print x*l+t
for i in f:print x*i+t[l-i]+x*q+t[i]+x*(q-i)+t[i]
print t[::-1]+x*q+t[0]
for i in f:print t[i]+x*q+t[l-i]+x*(i-1)+t[l-i]
print t

Python 3, 192 188 182

t=input()
x=" "
l=len(t)-1
q=l-1
p=print
f=range(q,0,-1)
p(x*l+t)
for i in f:p(x*i+t[l-i]+x*q+t[i]+x*(q-i)+t[i])
p(t[::-1]+x*q+t[0])
for i in f:p(t[i]+x*q+t[l-i]+x*(i-1)+t[l-i])
p(t)

นั่นคือ 203 ไบต์ นอกจากนี้คุณยังสามารถบันทึก 4 ไบต์โดยการแทนที่ด้วยraw_input() input()
acrolith

ถูกต้องแล้วขอบคุณ!
Joshua de Haan

x*(q)? คุณควรจะถอด parens ออกใช่ไหม
หมึกมูลค่า

คุณพูดถูกฉันโง่) ซ่อมมันตอนนี้ฮ่าฮ่า
Joshua de Haan

x*(i-1)->x*~-i
mbomb007

3

รหัสเครื่อง x86 (IA-32), 126 ไบต์

hexdump:

60 8b f9 57 33 c0 f2 ae 5e 2b fe 4f 87 fa 8d 1c
12 8b c3 48 f6 e3 c6 04 07 00 48 c6 04 07 20 75
f9 8b ea 4d 53 8d 04 2a 50 53 8b c5 f6 e3 8d 44
68 01 50 53 2b c2 8b c8 50 4b 53 55 53 03 c5 50
f7 d3 53 50 53 95 f6 e2 6b c0 04 50 43 53 51 6a
01 4a 52 6a 01 50 6a ff 51 b0 0a 6a 0b 8b dc 59
8b 6c cb fc 88 04 2f 03 2c cb 89 6c cb fc 83 f9
0a 75 01 ac e2 ea 4a 79 e0 83 c4 58 61 c3

นี่เป็นเวลาค่อนข้างนานดังนั้นเพื่ออธิบายฉันจะให้รหัส C ก่อน:

void doit(const char* s, char out[])
{
    int n = strlen(s);
    int w = 2 * n;
    int h = w - 1;
    int m = n - 1;

    memset(out, ' ', h * w);
    out[h * w] = 0;

    int offset1 = n + m;
    int offset2 = w * m + 2 * m + 1; // 2 * n * n - 1
    int offset3 = offset2 - n; // 2 * n * n - n - 1
    int offset4 = 4 * n * m; // 4 * n * n - 4 * n

    int offsets[] = {
        offset3, -1,
        offset4, 1,
        m, 1,
        offset3, 1 - w,
        offset4, -w,
        offset2 - 1, -w,
        offset2 - 1, w - 1,
        m, w - 1,
        offset3, w,
        offset2, w,
        offset1, w,
    };

    do
    {
        char c = *s++;
        for (int i = 0; i < 11; ++i)
        {
            if (i == 9)
                c = '\n';
            int offset = offsets[i * 2];
            assert(offset > 0 && offset < w * h);
            out[offset] = c;
            offsets[i * 2] += offsets[i * 2 + 1];
        }
    } while (--n);
}

ที่นี่ nคือความยาวของสตริงอินพุต

ขนาดของพื้นที่ส่งออกคือ2n(ความกว้าง) โดย2n-1(ความสูง) ก่อนอื่นมันเติมทุกอย่างด้วยช่องว่าง จากนั้นมันจะเดินทางไปตามเส้นตรง 11 เส้นในพื้นที่เอาท์พุทและเติมด้วยข้อความ:

  • 2 บรรทัดเต็มไปด้วยไบต์สิ้นสุดของบรรทัด (= 10)
  • 9 บรรทัดจะเต็มไปด้วยไบต์ที่ต่อเนื่องของสายป้อน

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

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

แหล่งประกอบ:

    pushad;

    ; // Calculate the length of the input string
    mov edi, ecx;
    push edi;
    xor eax, eax;
    repne scasb;
    pop esi; // esi = input string
    sub edi, esi;
    dec edi;

    ; // Calculate the size of the output area
    xchg edi, edx;  // edx = n
                    // edi = output string
    lea ebx, [edx + edx]; // ebx = w
    mov eax, ebx;
    dec eax; // eax = h
    mul bl; // eax = w * h

    ; // Fill the output string with spaces and zero terminate it
    mov byte ptr [edi + eax], 0;
myfill:
    dec eax;
    mov byte ptr [edi + eax], ' ';
    jnz myfill;

    mov ebp, edx;
    dec ebp; // ebp = m

    ; // Fill the array of offsets
    push ebx; // w
    lea eax, [edx + ebp];
    push eax; // offset1
    push ebx; // w
    mov eax, ebp;
    mul bl;
    lea eax, [eax + 2 * ebp + 1];
    push eax; // offset2
    push ebx; // w
    sub eax, edx;
    mov ecx, eax; // ecx = offset3
    push eax; // offset3
    dec ebx;
    push ebx; // w - 1
    push ebp; // m
    push ebx; // w - 1
    add eax, ebp;
    push eax; // offset2 - 1
    not ebx;
    push ebx; // -w
    push eax; // offset2 - 1
    push ebx; // -w
    xchg eax, ebp; // eax = m
    mul dl;
    imul eax, eax, 4;
    push eax; // offset4
    inc ebx;
    push ebx; // 1 - w
    push ecx; // offset3
    push 1;
    dec edx; // edx = n - 1
    push edx;
    push 1;
    push eax;
    push -1;
    push ecx;

    ; // Use the array of offsets to write stuff to output
myout:
    mov al, '\n';
    push 11;
    mov ebx, esp;
    pop ecx;
myloop:
    mov ebp, [ebx + ecx * 8 - 4];
    mov [edi + ebp], al;
    add ebp, [ebx + ecx * 8];
    mov [ebx + ecx * 8 - 4], ebp;
    cmp ecx, 10;
    jne skip_read;
    lodsb;
skip_read:
    loop myloop;
    dec edx;
    jns myout;

    add esp, 11 * 8;

    popad;
    ret;

ฉันใช้การคูณไบต์ที่นี่จำกัดความยาวของสตริงอินพุตที่ 127 ซึ่งจะช่วยหลีกเลี่ยงการลงทะเบียนซ้ำซ้อนedx- ผลิตภัณฑ์จะถูกคำนวณaxแทน

ความผิดพลาดเล็กน้อย: เมื่อเติมอาร์เรย์ความยาวของสตริงจะลดลง 1 ดังนั้นฉันจึงปรับเงื่อนไขการออกจากลูป:

    jns myout

มันนับเป็น -1


3

Ruby, 148 144 ไบต์

+1 ไบต์จากnแฟล็ก แสดงบรรทัดใหม่แทนเครื่องหมายอัฒภาคเพื่อให้อ่านได้ (ฟังก์ชันการทำงานเดียวกัน)

S=" "
X=S*s=$_.size-2
puts X+S+I=$_,(r=1..s).map{|i|c=I[~i];S*(s-i+1)+I[i]+X+c+S*~-i+c},I.reverse+X+I[0],r.map{|i|c=I[i];I[~i]+X+c+S*(s-i)+c},I

ทำงานอย่างนั้น อินพุตเป็นบรรทัดของ STDIN โดยไม่มีการขึ้นบรรทัดใหม่ดังนั้นจึงจำเป็นต้องมีการไพพ์จากไฟล์

ruby -ne 'S=" ";X=S*s=$_.size-2;puts X+S+I=$_,(r=1..s).map{|i|c=I[~i];S*(s-i+1)+I[i]+X+c+S*~-i+c},I.reverse+X+I[0],r.map{|i|c=I[i];I[~i]+X+c+S*(s-i)+c},I'

1

Javascript, 225 198 ไบต์

บันทึกแล้ว 27 ไบต์ขอบคุณ @Neil

f=(s,l=s.length-2,d=' ',r='repeat',t=d[r](l))=>[d+t+s,...a=[...Array(l)].map((_,i)=>d[r](l-i)+s[i+1]+t+(p=s[l-i])+d[r](i)+p),[...s].reverse().join``+t+s[0],...a.map(v=>v.trim()).reverse(),s].join`
`
  • [... ] แทนที่จะเป็น. catcat
  • [ ... ] + map แทนสำหรับวนซ้ำ
  • เพียงหนึ่งคำสั่งโดยการย้ายตัวแปรเป็นพารามิเตอร์ฟังก์ชั่น
  • การเริ่มต้นที่ดีขึ้นสำหรับlและt

คำตอบเดิม:

f=s=>{l=s.length,d=' ',r='repeat',a=[],t=d[r](l-2)+s;for(i=1;i++<l-1;)a.push(d[r](l-i)+s[i-1]+d[r](l-2)+(p=s[l-i])+d[r](i-2)+p);console.log(d+[t].concat(a,[...t].reverse().join``+s[0],a.map(v=>v.trim()).reverse(),s).join`
`)}

1
ดีแม้ว่าเล่นได้: (s,l=s.length-2,d=' ',r='repeat',t=d[r](l))=>[d+t+s,...a=[...Array(l)].map((_,i)=>d[r](l-i)+s[i+1]+t+(p=s[l-i])+d[r](i)+p),[...s].reverse().join``+t+s[0],...a.map(v=>v.trim()).reverse(),s].join`\n`(ใช้\nเพราะคุณไม่สามารถใส่บรรทัดใหม่ในความคิดเห็น)
Neil

0

Java 7, 283 ไบต์

void a(String s){int h=s.length(),n=h*2-1,t=n-h,u=n-1;char[][]c=new char[n][n];for(int i=0;i<h;i++){c[0][t+i]=c[i][t-i]=c[t][t-i]=c[t+i][t]=c[t+i][u-i]=c[t-i][t+i]=c[t-i][u]=c[u][i]=c[u-i][0]=s.charAt(i);}for(int y=0;y<n;y++){System.out.println(new String(c[y]).replace('\0',' '));}}

ลองที่นี่!

Ungolfed:

void a(String s) {
    int length=s.length(),
        n=length*2-1,
        mid=n-length,
        doubleMid=n-1;
    char[][]c=new char[n][n];
    for(int i=0;i<length;i++) {
        c[0][mid+i]= 
        c[i][mid-i]=
        c[mid][mid-i]=
        c[mid+i][mid]=
        c[mid+i][doubleMid-i]=
        c[mid-i][mid+i]=
        c[mid-i][doubleMid]=
        c[doubleMid][i]=
        c[doubleMid-i][0]=s.charAt(i);
    }
    for(int y=0;y<n;y++){
        System.out.println(new String(c[y]).replace('\0',' '));
    }
}
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.