시간 여행의 역설


17

한 남자에게는 두 개의 장치가 있습니다.

  • 타임머신 -그는이 머신을 생각함으로써 제어 할 수 있습니다. 이를 통해 과거 또는 미래의 특정 시점 (또는 현재 시점)으로 어느 시점에서든 다른 시점으로 이동할 수 있습니다. 그가 B에서 A로 과거로 여행하는 경우 A에서 B까지의 모든 일반 이벤트 (타임머신, 교류 발전기 제외)는 정확히 같은 방식으로 반복되어야합니다. 그런 다음 B 지점에서 A 지점으로 다시 이동합니다. 따라서 한 번의 시간 이동으로 무한 루프가 생성됩니다.
  • 발전기 -이 문제를 깨닫고 다른 기계를 만듭니다. 그는 모든 육체적 사건이 반복적으로 반복 되더라도 그의 생각은 다를 수 있음을 알고있다. 따라서이 기계는 생각으로도 제어 할 수 있도록 설계되었습니다. 기계는 언제든지 사용 된 시간과 관련하여 대체 미래를 제공하기 위해 사용될 수 있습니다.

긴 예제를 사용하여 모든 세부 사항을 설명하겠습니다.

1000 T+250 250 T+0 500 T-200 100 T-50 125 A 225 T-400 500 A 100 T-200 150 T-25 100 T+100 50 A 25
  • 1000 년이 지났습니다. 지금은 1000 년입니다.
  • 그는 1000에서 1250까지 여행합니다.
  • 250 년이 지났습니다. 지금은 1500 년입니다.
  • 그는 1500에서 1500으로 이동합니다. 이것은 효과가 없으며 무시할 수 있습니다.
  • 500 년이 지났습니다. 지금은 2000 년입니다
  • 그는 2000 년에서 1800 년을 여행합니다.
  • 100 년이 지났습니다. 지금은 1900 년입니다.
  • 그는 1900 년에서 1850 년까지 여행합니다.
  • 125 년이 지났습니다. 그러나 이번에는 그가 루프에 있기 때문에 상황이 다릅니다. 50 년은 1850 년에서 1900 년까지지나갑니다. 그는 1850 년으로 되돌아갑니다. 또 다른 50 년은 1850 년에서 1900 년까지지나갑니다. 25 년이 지났고 1875 년이므로 125 년이 걸립니다.
  • 그는 발전기를 사용합니다. 지금은 1875 년의 다른 미래가 있으며, 현재는 과거입니다. 과거는 변하지 않았습니다.
  • 225 년이 지났습니다. 지금은 2100 년입니다.
  • 그는 2100에서 1700으로 여행합니다.
  • 500 년 통과 : 1700 년에서 1875 년까지 175 년이 정상적으로지나갑니다. 그는 발전기를 다시 만나지 않았다. 이는 1875 년 이후 3 번째 미래가 만들어 졌음 을 의미한다 . 325 년이 정상적으로지나 2200 년이됩니다.
  • 아직 정의되지 않은 2200에 대한 미래는 하나뿐이므로 교류 발전기를 사용해도 효과가 없으며 무시해도됩니다.
  • 100 년이 지났습니다. 이제 2300입니다.
  • 그는 2300에서 2100으로 여행합니다.
  • 150 년 통과 : 2100 년에서 2200 년까지 정상적으로 통과하는 100 년. 두 번째 미래는 2200 년부터 창출됩니다. 50 년이 지났으며 현재는 2250 년입니다.
  • 그는 2250에서 2225로 가야한다. 그러나 이제 두 개의 다른 타임 라인에 두 개의 2225가 존재한다. 그러므로 우리는 그가 어느 시점에 도달 할 것인지 결정할 수 없기 때문에 역설로 이어진다. (우리는 그가 더 최근의 타임 라인으로 간다고 가정하지 않을 것입니다.) 따라서 시뮬레이션이 종료됩니다.
  • 100 T+100 50 A 25역설이 일어 났고 시뮬레이션 실행이 중단되어 더 이상 아무것도 무시됩니다.

힌트 : 예를 이해하기 위해 고군분투하고 있다면, 땅에서 파고있는 길과 같은 시간을 상상해보십시오. 시간 여행을한다면 텔레 포터를 만드는 것입니다. 교류기를 사용하는 경우 기존 경로의 벽에 새 경로를 파고 있습니다.

역설

A, B 및 C가 세 시점이라고 가정합니다. 역설이 iff로 발생했다고합니다.

  • C 지점에 있고 B 지점에 교류 발전기가 있고 B 지점에 대한 미래가 둘 이상 존재하며 그 중 하나에있을 때 시간 여행을 통해 B와 C 사이의 모든 지점에 액세스하려고합니다.
  • A 지점에 있고 B 지점에 발전기가 있고 B 지점에 대한 미래가 둘 이상 존재하며 시간 여행을 통해 B 지점 (B 이후)에 액세스하려고합니다.

입력

예제와 유사한 일련의 이벤트. (형식이 유연합니다.)

산출

역설이 발생했는지 여부를 나타내는 진실 / 거짓 값입니다.

도전

가장 짧은 코드 (바이트)가 이깁니다.


어떻게 flexibleformat?
고양이

@ GlennRanders-Pehrson 아, 네가 무슨 뜻인지 알았어. 편집했습니다.
ghosts_in_the_code

2
@sysreq 입력에 허용되는 추가 구두점 (공백, 쉼표, 대괄호 등). 시간 여행과 발전기를 구별 할 수있는 모든 문자. + 및-(앞으로 / 뒤로 이동) 대신 모든 문자를 사용할 수 있습니다. 숫자는 임의의 밑 (이진수, 10 진수 등) 일 수 있습니다. 이벤트는 같은 순서로만 입력됩니다. 실제 연도 번호는 제공되지 않으며 start는 0 (또는 다른 정수)으로 가정하고 실제 연도 숫자를 직접 파악해야합니다 (필요한 경우).
ghosts_in_the_code

하나의 큰 예제 대신 작은 예제가 여러 개 있으면 도움이되지만 여전히 투표했습니다!
밝게 돈

답변:


4

루비, (510) 460 바이트

p=[0];w=[n=x=0]
i=gets.split.map{|s|
if x!=1
if s[0]=="A"
w<<n
else
if s[0..1]=="T+"
t=n
q=s[2..-1].to_i
if w[-1]==t||(w[-1]>t&&w[-1]<n+q)
w<<w[-1]
n+=q
else
n+=(t<p[-1]&&n+q>p[-1])?q%(p[-1]-n):q
end
elsif s[0..1]=="T-"
t=n
p<<n
n-=s[2..-1].to_i
x=(x==0&&w[-1]>0&&t>w[-1]&&n>w[-1])?1:0
else
t=n
q=s.to_i
if w[-1]==t||(w[-1]>t&&w[-1]<n+q)
w<<w[-1]
n+=q
else
n+=(t<p[-1]&&n+q>p[-1])?q%(p[-1]-n):q
end
end
end
else
break
end}
p x

입력

예를 들어

산출

0 = 역설 없음, 1 = 역설

견본

제공된 샘플 입력 : 1000 T+250 250 T+0 500 T-200 100 T-50 125 A 225 T-400 500 A 100 T-200 150 T-25 100 T+100 50 A 25 returns 1, 역설이 발생했음을 나타냅니다.

노트

이것은 내가 시도한 첫 번째 연습 만 아니라 내가 작성한 최초의 루비 프로그램이기도합니다. 따라서 아마도 더 짧을 수도 있습니다.

간단한 설명

p: Infinite loops
w: Alternate timelines
n: Now (regardless of timeline)
x: Paradox

무한 루프는 정시에 진행하는 동안에 만 발생합니다. 피드백을 보내 주셔서 감사합니다. 특히이 문제를 해결하는 더 좋은 방법을 지적하고 있다면 더욱 그렇습니다.


샘플 입 / 출력 데이터를 제공 할 수 있습니까?
애디슨 크럼프

@VoteToClose-질문에 제공된 데이터 외에도 필요한 경우 더 많은 샘플 데이터를 만들 수 있습니까?
피터 Abolins

어머나, 그 "샘플"부분을 완전히 놓쳤다. 나는 바보입니다. 한
애디슨 크럼프

3
모두 then불필요하며 제거 할 수 있습니다. 또한 더 많은 문자를 저장 하는 {...}대신 사용해야합니다 do...end. map이상의 바이트를 저장 each하고, split기본적으로 공백에 분할. 초기화의 처음 네 줄은로 단축 될 수 있습니다 p=[];w=[n=x=0].
Doorknob

2
나는 3.5 년이 지났음을 알고 있지만 (Lol ..) 현재 코드를 288 바이트로 골프를 수 있다고 생각합니다 (루비를 잘 모르기 때문에 확실하지는 않습니다). 그러나 현재 코드는 앞으로 시간 여행 (OP 설명의 두 번째 글 머리 기호)이있는 역설을 설명하지 않습니다.
Kevin Cruijssen

3

05AB1E , 93 92 86 82 바이트

ðU0V#vyAQiYˆðUëy.ïiYy+DX˜såàiXD€нY@Ïн©θ-®¥OÄ%®θY-YOVëVëYy¦+©¯@àXðʘà*i1q}XY®Ÿª{U®V

교류 발전기 Aabcdefghijklmnopqrstuvwxyz대신 바이트를 저장 한다는 점을 제외하면 입력은 도전 설명과 동일한 형식 입니다. 역설이 발생한 경우
출력 1하거나 그렇지 않은 경우 입력 자체를 출력 합니다 ( 105AB1E 에서만 정직하고 다른 모든 것은 거짓 임).

내 Java 10 답변을 느슨하게 기반으로 합니다.

온라인으로 사용해보십시오.

(또는 추가 디버그 라인에 온라인으로 시도 TODO : 한 번에 모든 테스트 케이스와 적절한 테스트 스위트를 생성합니다 .. )
- 테스트 케이스를 뒤로 시간 여행의 역설 : 온라인으로보십시오.
-정시 여행 역설이있는 테스트 사례 : 온라인으로 사용해보십시오.
-시간 여행 역설이없는 테스트 사례 : 온라인으로 사용해보십시오.

설명:

ðU                         # Set variable `X` (time-travels) to a space character " "
0V                         # Set variable `Y` (current year) to 0
#                          # Split the (implicit) input by spaces
 v                         # And loop over each event `y`:
  yAQi                     #  If the current event `y` is an alternator ("abcdefghijklmnopqrstuvwxyz"):
      Yˆ                   #   Add the current year `Y` to alternators-list `GB`
      ðU                   #   And reset variable `X` to " "
  ëyi                    #  Else-if the current event `y` is an integer:
       Yy+                 #   Calculate the current year `Y` plus the integer `y`
          D                #   Duplicate `Y+y`
           X˜såài          #   If this `Y+y` is within any of the time-travel ranges:
                 X €н      #    Get the starting positions of each time-travel
                     Y@    #    Check for each starting position if the current year `Y` is >= it
                  D    Ï   #    And only leave the time-travel ranges for which this is truthy
                        н  #    Then pop and push the first one
                         © #    Store this time-travel range in variable `r` (without popping)
                 θ         #    Pop and only leave the time-travel destination
                  -        #    Subtract it from the `Y+y` we duplicated
                       %   #    And modulo it with:
                   ®¥OÄ    #     The absolute distance of the time-travel `r`
                 ®θ        #    Then push the time-travel destination again
                   Y-      #    And subtract the current year `Y`
                 YO        #    Then sum these two and the current year `Y` together
                   V       #    And pop and store it as new year `Y`
       ë                   #   Else (`Y+y` is not within any time-travel ranges)
        V                  #    Simply pop and store the duplicated `Y+y` as new year `Y`
  ë                        #  Else (the current event `y` is a time-travel)
    y¦                     #   Remove the leading "T"
   Y  +                    #   And add the value to the current year `Y`
       ©                   #   Store this value in variable `r`
        ¯@à                #   Check if any alternator in list `GB` is >= this value
           XðÊ˜à           #   Check if there are any time-travels
                *i  }      #   And if both are truhy:
                  1        #    Push a 1
                   q       #    Stop the program
                           #    (after which the top of the stack is output implicitly)
    Y®Ÿ                    #   Create a list in the range [current year `Y`, new year `r`]
   X   ª                   #   Append it to the time-travels `X`
        {                  #   And then sort these time-travels
         U                 #   After which we pop and store it as updated `X`
   ®V                      #   And then set `Y` to the new year `r`
                           # (if we haven't reached `q`, the (implicit) input is output instead)

3

자바 10, 498 485 478 바이트

import java.util.*;s->{var a=new Stack<Long>();var m=new TreeMap<Long,Long>();long p=0,c=0,t,v,k;o:for(var S:s.split(" "))if((t=S.charAt(0))>65){var b=S.charAt(1)>44;v=new Long(S.substring(2));for(var A:a)p=A>c+(b?-v:v)|m.size()<1?p:1;if(v>0)m.put(c,b?c-v:c+v);c+=b?-v:v;}else if(t>64){a.add(c);m.clear();}else{t=new Long(S);e:for(var e:m.entrySet())if((k=e.getKey())>=c){for(v=c;v<=c+t;)if(a.contains(v++))break e;c=(v=e.getValue())+(c+t-v)%(k-v);continue o;}c+=t;}return p>0;}

입력은 현재 도전 과제 설명과 같은 형식으로되어 있습니다.

@BenjaminUrquhart 덕분에 -13 바이트 . @ceilingcat
덕분에 -7 바이트 .

온라인으로 시도 하거나 추가 된 디버그 라인으로 온라인으로 시도하십시오 .

설명:

import java.util.*;            // Required import for the List and TreeMap
s->{                           // Method with String parameter and boolean return-type
  var a=new Stack<Long>();     //  Create a List for the alternators
  var m=new TreeMap<Long,Long>();
                               //  Create a sorted Map for the time-travels
  long p=0,                    //  Paradox-flag, initially 0
       c=0,                    //  Current year, initially 0
       t,v,k;                  //  Temp-values, uninitialized
  o:for(var S:s.split(" "))    //  Loop over the input substrings split by space:
    if((t=S.charAt(0))>65){    //   If the first character is a 'T':
      var b=S.charAt(1)>44;    //    Check if the second character is a '-'
      v=new Long(S.substring(2));
                               //    Convert the String-value to a number
      for(long A:a)            //    Loop over the alternators
        p=A>                   //     If an alternator is larger than:
            c+                 //      The current year, plus
              (b?              //      If we travel backwards in time:
                 -v            //       Subtract the value
                :              //      Else (we travel forward in time):
                 v)            //       Add the value
          |m.size()<1?         //     Or if no previous time-travels occurred:
           p                   //      Leave the paradox-flag the same
          :                    //     Else:
           1;                  //      Set the paradox-flag to 1
      if(v>0)                  //     If the value is not 0 (edge-case for "T+0")
        m.put(c,b?c-v:c+v);    //      Add the from-to time-travel to the Map
      c+=b?-v:v;}              //     Increase/decrease the year accordingly
    else if(t>64){             //   Else-if the character is an 'A':
      a.add(c);                //    Add the current year to the alternators-list
      m.clear();}              //    And empty the time-travel Map
    else{                      //   Else (it's a number)
      t=new Long(S);           //    Convert the String to a number
      e:for(var e:m.entrySet())//    Loop over the time-travels:
        if((k=e.getKey())      //     If the time-travel starting point is
                         >=c){ //     larger than or equal to the current year
          for(v=c;v<=c+t;)     //      Loop from the current year to the year+number:
            if(a.contains(v++))//       If the alternator-list contains any of these years
              break e;         //        Stop the time-travel loop
          c=                   //      Set the current year to:
             (v=e.getValue())  //       The time-travel destination
             +                 //       Plus:
              (c+t             //        The current year plus the number
                  -v)          //        minus the time-travel destination
                     %(k-v);   //        Modulo the time-travel from-to distance
          continue o;}         //      And then continue the outer input-loop
      c+=t;}                   //    Increase the current year by the number 
  return p>0;}                 //  Return whether the paradox-flag is 1

왜 사용하지 Long않습니까?
Benjamin Urquhart 12

1
@ BenjaminUrquhart 좋은 질문입니다. 처음에 내 목록과 맵은 원시 형식이므로 int짧았지만 map-Entry 키 값 쌍에 오류가 발생했습니다. 그 후 모든 것을 Long으로 바꾸는 것에 대해 생각하지 않았습니다. -13 주셔서 감사합니다!
Kevin Cruijssen
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.