2012-12-12 5 views
3

내가 같은 멀티 quine을 정의하고있다 :복잡한 다중 퀸은 어떻게 쓰여 집니까?

더 입력을 제공하지 않을 때 그들의 각 하나는, 정확한 소스 코드를 출력하도록 N 서로 다른 프로그래밍 언어에서 N 프로그램의 집합, n을 입력하면 * n * 번째 프로그램의 소스 코드를 출력합니다.

첫 번째 프로그램이 출력 될 때까지 각 프로그램이 다음 프로그램의 소스 코드를 출력하는 프로그램의 순환 순서와 혼동해서는 안됩니다. 이 예에서 각 프로그램은 하나의 퀸이 아니며 그 점을 무시합니다. 이 순환 세트는 n의 높은 값에 대해 흥미로운 brainteasers 인 동시에 구현하기가 쉽지 않습니다.

는 단지,이 경우, " 2. 이상인 N의 값"을 의미 나는 n = 2에 대한 해결책이이 경우에 충분히 복잡하다고 믿습니다. 그러나 n의 모든 값에 대한 일반적인 해결책 (읽기 : 전략)이 대상입니다.

나는 "간단한"퀸이 어떻게 쓰여지는지 알지만, 나는 복잡한 멀티퀸 주위에서 머리를 터는 것처럼 느껴진다. 그것은 나를 매료시킨다. 프로그래머의 마음 속에 떠오르는 독창적 인 독창성을 제외하고는 해결책이 없다고 생각합니다.

+0

이 답변을 얻는 가장 좋은 방법은 codegolf.SE로 이동하여 사람들에게 멀티 쿼 인 쓰기를 시도하도록 요청하는 것입니다. 평가 기준을 설정합니다 (min (s/n), n> = 2). 여기서 s는 코드 크기이며 응답을 기다립니다. :) –

+0

@ 빅터 어쩌면 해결책을 얻는다면 사실이지만, 나는 못 생기고, 짧고, 모호한 멀티 퀸에 관심이 없다. 나는 실제로 솔루션에 관심이 없다. 그러나 오히려 어떻게 솔루션이 만들어 졌는가? 그래서 나는 좀 더 많은 대답을 기대한다고 인정해야하지만 코드 늑대보다는 질문을 여기에 넣었습니다.) – Swadq

답변

4

퀸, 다국어 퀸, 멀티 퀸에 특별한 것은 없습니다. 그들은 모두 거의 자동으로 작성 될 수 있습니다.

예를 들어, C++의 늪지대 표준, 장황하고, 우아하고 비효율적 인 비효율적 인 quine이 있습니다. 그러나 모든 단점을 감안할 때 우리가 원하는 것을하기가 쉽습니다.

#include <iostream> 
#include <string> 
#include <cstdlib> 

std::string show (const std::string& in) { 
    std::string res = "\""; 
    for (std::string::const_iterator it = in.begin(); it < in.end(); ++it) { 
     switch (*it) { 
      case '"': 
      case '\\': 
       res += '\\'; 
      default: 
       res += *it; 
     } 
    } 
    res += "\""; 
    return res; 
} 

int main (int argc, char* argv[]) 
{ 
    std::string arr[] = { // beginning ends here 
"#include <iostream>", 
"#include <string>", 
"#include <cstdlib>", 
"", 
"std::string show (const std::string& in) {", 
" std::string res = \"\\\"\";", 
" for (std::string::const_iterator it = in.begin(); it < in.end(); ++it) {", 
"  switch (*it) {", 
"   case '\"':", 
"   case '\\\\':", 
"    res += '\\\\';", 
"   default:", 
"    res += *it;", 
"  }", 
" }", 
" res += \"\\\"\";", 
" return res;", 
"}", 
"", 
"int main (int argc, char* argv[])", 
"{", 
" std::string arr[] = { // beginning ends here", 
"======", 
" };", 
" int n = argc == 1 ? 0 : std::atoi(argv[1]);", 
" if (n == 0) {", 
"  int i, j;", 
"  for (i = 0; arr[i] != \"======\"; ++i) std::cout << arr[i] << std::endl;", 
"  for (j = 0; j < sizeof(arr)/sizeof(arr[0]); ++j) std::cout << show(arr[j]) << ',' << std::endl;", 
"  for (++i; i < sizeof(arr)/sizeof(arr[0]); ++i) std::cout << arr[i] << std::endl;", 
" } else {", 
" }", 
"}", 
    }; 
    int n = argc == 1 ? 0 : std::atoi(argv[1]); 
    if (n == 0) { 
     int i, j; 
     for (i = 0; arr[i] != "======"; ++i) std::cout << arr[i] << std::endl; 
     for (j = 0; j < sizeof(arr)/sizeof(arr[0]); ++j) std::cout << show(arr[j]) << ',' << std::endl; 
     for (++i; i < sizeof(arr)/sizeof(arr[0]); ++i) std::cout << arr[i] << std::endl; 
    } else { 
    } 
} 

당신이 볼 수 있듯이,이 프로그램의 핵심은 문자열을 사용하고, C++ 문자로서의 표현을 반환 show라는 작은 기능입니다. 전체적인 구조는 다음과 같습니다. 문자열 배열의 시작 부분을 인쇄합니다. show을 통해 파이프 된 전체 배열을 인쇄하십시오. 배열의 끝 부분을 인쇄하십시오. 문자열 배열은 프로그램의 중간에 삽입 된 프로그램의 복사본입니다. 초기 부분은 프로그램에서 복사되지 않은 특수한 "=====" 문자열로 마지막 부분과 분리됩니다 (show을 통해 한 번만 인쇄됩니다).

다른 문구를 다른 언어로 인쇄하는 것과 같은 추가 작업을 쉽게 삽입 할 수 있습니다. 나는 그러한 행동을위한 자리 표시자를 삽입했다.

이제 이것을 임의의 프로그래밍 언어 (예 : FORTRAN)로 변환하는 것이 중요합니다. 우리가 해냈다 고 가정하면, 그것은 라인 L1, L2, ..., LN으로 구성됩니다. 다음 문을 자리 표시 자에 삽입합니다.

std::cout << "L1" << std::endl; 
std::cout << "L2" << std::endl; 
... 
std::cout << "LN" << std::endl; 

문자열 배열을 적절하게 수정합니다. 우리는 커맨드 라인 인수에 따라 자체적으로 인쇄 할 수있는 quine과 FORTRAN의 quine을 가지고 있습니다.

좋아, FORTRAN quine은 어떻습니까? C++이 아닌 자체 인쇄 만 가능합니다. 문제는 없지만, C++ quine을 FORTRAN quine으로 다시 복사 해 봅시다.

그러나 C++ quine에는 이미 전체 FORTRAN 퀴 인이 포함되어 있습니다. 두 번?

문제가 없으면 으로 FORTRAN quine은 이미으로 인쇄 할 수 있습니다. 따라서 원래의 C++ 라인을 FORTRAN으로 다시 복사하기 만하면됩니다. FORTRAN을 다시 한번 (또는 두 번) 복제 할 필요가 없습니다.

FORTRAN을 약간 수정하면됩니다. , std::cout << "Li" << std::endl;로 한 번 Li로 한 번 단지 C++ quine이 그것을 가지고 같은 : 우리는 C++의 quine를 인쇄하려면 FORTRAN의 quine을 요청하면 또한 모든 FORTRAN 라인, 두 번를 모든 C++ 선을 인쇄해야합니다. 그런 다음 C++ quine (FORTRAN quine 포함)을 다시 얻습니다.

또한 FORTRAN 수정 사항을 다시 C++로 전달해야합니다 (즉, std::cout << "Li" << std::endl; 행 수정). 그리고 수정의 물결이 여기서 멈 춥니 다.

이제 명령 줄 인수에 따라 자체 또는 서로 인쇄 할 수있는 두 개의 프로그램이 있습니다.

나는이 모든 것을 실제로하도록 권장합니다.