KLDP Code Fest/Theme Coding
점수 (여러 번 제출하신 분은 모두 최종 답안 기준)
코드 퍼즐 제출하신 답
1. cdpark 님 ¶
#include <stdio.h>
#include <stdlib.h> #define h(x) x+(x>9?55:48) void o(int n) { n?o(n/N),putchar(h(n%N)):0; } int main() { o(strtol(X,0,M)); return 0; }
#include <stdio.h>
void o(int n) { n?o(n/N),putchar(n%N+(n%N>9?55:48)):0; } int main() { char *x=X; int n=0; do { n*=M; n+=*x<97?*x-48:*x-87; } while (*++x); o(n); return 0; }
2. mithrandir 님 ¶
#include <stdio.h>
#define b a/i #define c X[i] int main () { int a=0, i=0; while (c) { a *= M; a += (c <= 57)?c-48:c-87; i++; } i = 1; while (a / (i *= N)); while ((i/=N)>0) { putchar (b<=9 ? b+48 : b+97); a %= i; } }
3. 서상현 님 ¶
#include <stdio.h>
int main() { char *x = X; int s = 0, i = 1; do { s *= M; s += (*x-(*x<'a'?'0':'a'-10)); } while (*++x); do { i *= N; } while (i * N < s); while (i) { putchar(s/i+(s/i<10?'0':'a'-10)); s %= i; i /= N; } }
4. sliver 님 (우승) ¶
#include <stdio.h>
void p(int v,int i) { v ? (p(v/N,1),v%=N,v += v<10 ? '0' : 'a'-10,putchar(v)) : 0; if(!i) { for(;X[i];i++) v = M*v + (X[i] <= '9' ? X[i]-'0' : X[i]+10-'a'); v ? p(v,1) : putchar('0'); } } int main() { p(0,0); }
5. yui 님 ¶
#include <stdio.h>
#define to_num( d ) ( ( d < '9') ? ( d - '0') : ( d - 'a'+10)) #define to_char( d ) ( (d > 10) ? ('a' + d - 10) : ( d + '0')) int main() { int v=0, i=0; while(X[i]){ v+=to_num(X[i]); v*=M; ++i; } v/=M; i=v; while (i > N) { int k = 1; while(v > N) { v= v/ N; k*=N; } putchar(to_char(v%N)); v = i - k*(v%N); i = v; v = i; } putchar(to_char(v%N)); }
6. 토끼군 ¶
#include<stdio.h>
int i,s; int Q() { return s % N + 48 + (s % N > 9) * 7 + (s / N ? s /= N, putchar(Q()), 0 : 0); } int main() { while( X[i] ) s = M * s + X[i] - (X[i++] < 64 ? 48 : 87); return putchar(Q()); }
7. 기타 잡담 ¶괜히 짧게 짜는 사소한 고민만 하다가 결국 못 제출했는데.. 그 중의 한 가지가, <stdio.h>보다 int putchar(int);를 쓰는 편이 1글자 줄더군요. -cwryu
int putchar();로 하면 4글자 줄일 수 있습니다. C에서만 허용되는.. -perky
아! 그 생각을 못 했군요 --토끼군
짧게 쓰는걸 해보질 않아 습관대로 짜서 냈네요. 테스트 좀 해보고 잘 되길래 그냥 제출했습니다. 압도적(?)인 길이군요. 흐흐. -- yui
토끼군 님의 프로그램엔 약간 위험한 코드가 들어 있습니다. Q 함수 내부에 s에 대한 할당이 있습니다. C 언어 문법만으로는 (s /= N) 부분의 계산이 나중에 될 거라는 보장이 없습니다. - cdpark
네. 컴파일만 되고 제대로 실행되는 지만 확인했기 때문에 보장은 할 수 없을 겁니다. (gcc에서는 되었지만 어디서 어떤 일이 터질 지 아무도 모르는 폭탄 코드...랄까요. 쿨럭.) --토끼군
7.1. cdpark (마감후 버젼의 개량판1) ¶
int putchar();
void o(int n) { n?o(n/N),putchar(n%N+(n%N>9?55:48)):0; } int main() { char *x=X; int n=0; do { n=n*M+*x-48-(*x>64)*39; }while(*++x); o(n); } 토끼군 님 버젼을 비슷한 규칙(stdio.h 제거,...)으로 고친것보다 1 byte 짧습니다. 그러나 변수는 세개. 시상식 이전까지 만들었던 버젼입니다. submit은 안 했고..
7.2. cdpark (ultimate 판) ¶
int putchar();
void f(char *x,int n) { *x?f(x+1,n*M+*x-48-(*x>64)*39) :n?f(x,n/N),putchar(n%N+48+(n%N>9)*7):0; } int main() { f(X,0); } 퍼키 님이 원한 소스가 이거겠죠? 변수 두개! 전역변수 없음! 점수는 대략 60 점? -- cdpark
warning이 나도 상관없다면 함수선언앞에 void랑 int빼도 될듯합니다. -- byteme
대회 규칙에 -c99 -Werror 옵션이 있답니다. -- cdpark
초고수님들의 암호같은 소스를 보고 있자니 눈이 돌아가고 머리가 깨질 것 같군요. 소스에 대한 해설을 덧붙여주셨으면 좋겠습니다. --세벌
서상현님의 코드가 가장 기본적인 형태라고 할 수 있을 겁니다. 먼저 M진수 X를 10진수로 변환하고, 그 10진수를 다시 N진수의 수로 변환하는 겁니다. 서상현님 코드의 첫번째 do-while loop이 10진수로 변환하는 코드고, 마지막 while loop이 다시 N진수로 변환하는 코드입니다. (가운데 do-while loop은 N진수로 변환하기 전의 준비작업)
다른 분들의 코드도 기본적으로 같은데, 코드 길이를 줄이기 위해서 loop을 recursion으로 표현하는 방법을 사용한 겁니다. (대부분이 두번째 단계, N진수로 변환하는 코드를 recursion으로 표현하고 있습니다.)
개인적으로 cdpark님의 ultimate판은 특이(?)하게 생긴 코드라고 생각하지만 프로세스는 동일합니다. -- kane
|
When the wind is great, bow before it; when the wind is heavy, yield to it. |