8
\$\begingroup\$

Background

Inspired by a now deleted question by John Burger from which I quote:

Good book! IF you can wait 7,143 years...

Now obviously no human made this mistake. It's a mis-decode of something - perhaps the ISBN? My question is: does anyone know of an existing algorithm that was so messed up it would invent an entirely new calendar?

TFeld ingeniously commented:

It seems that the book was published on 2008-09-16, so maybe it was somehow read as 00809162 -> 00=dec?, 80, 9162

Task

Given a date represented as a three-element list, answer with the corresponding three-element mis-decoded list.

Mis-decoding happens as follows (example for [2008,9,16] in parentheses):

  1. Join the digits of the year, month, and day, inserting leading zeros as necessary ("20080916")

  2. Move the first digit to the end ("00809162")

  3. Split the eight digits into groups of two, two, and four ("00","80","9162")

  4. Interpret them as numbers ([0,80,9162])

  5. Normalise the month number by wrapping 0 around to 12, and wrapping 13 around to 1, 14 to 2, 15 to 3, …, 25 to 1 etc. ([12,80,9162])

  6. Rearrange the list to get the original order ([9162,12,80])

    • You may take the original date in any order, but your answer must use the same order. Please state any non-default order.

    • The given year will always have four digits, but dates in October will lead to a three- or two-digit answer year.

    • You may take a list of strings or a character-delimited string, but it may not include leading zeros and you must answer in the same format and again without leading zeros.

Examples

[1700,1,1][1011,10,0]

[1920,4,29][4291,8,0]

[1966,11,27][1271,12,61]

[1996,12,13][2131,3,61]

[2008,9,1][9012,12,80]

[2008,9,16][9162,12,80]

[1010,10,1][11,1,1]

\$\endgroup\$
12
  • \$\begingroup\$ Can we take the input as a list of strings? \$\endgroup\$ Jan 7, 2019 at 16:42
  • \$\begingroup\$ @WindmillCookies Yes, but then they may not include leading zeros, and you must answer with a list of strings (without leading zeros) too. \$\endgroup\$
    – Adám
    Jan 7, 2019 at 16:45
  • \$\begingroup\$ Is it okay if the program prints the numbers separated by spaces to stdout? \$\endgroup\$ Jan 7, 2019 at 16:55
  • \$\begingroup\$ @fəˈnɛtɪk What does your input/argument look like? \$\endgroup\$
    – Adám
    Jan 7, 2019 at 17:17
  • 1
    \$\begingroup\$ @Adám Ah, I wasn't sure if when you said "The year will always have four digits." you were referring to input, output, or both \$\endgroup\$
    – Neil A.
    Jan 7, 2019 at 23:23

11 Answers 11

3
\$\begingroup\$

Python 2, 95 67 66 65 64 bytes

lambda y,m,d,t=10,T=1000:(m%t*T+d*t+y/T,y%T/t%12or 12,y%t*t+m/t)

Try it online!

-1 byte, thanks to Chas Brown


Given the task description, I kinda had to try it :)

\$\endgroup\$
0
2
\$\begingroup\$

C# (Visual C# Interactive Compiler), 69 bytes

(y,m,d)=>(m%10*1000+d*10+y/1000,(d=y%1000/10%12)<1?12:d,y%10*10+m/10)

Try it online!

Lambda with 3 inputs (y,m,d) that returns a 3-value tuple that has the resulting date parts in the same order.

The result is calculated by shifting digits to the left and right using regular division and the modulo operator with different powers of 10.

The d variable is used to caputure the month calculation so that it can be returned or wrapped to 12 when 0.

\$\endgroup\$
1
\$\begingroup\$

JavaScript, 74 72 65 bytes

Thanks @Shaggy for saving 2 bytes Thanks @Arnauld for saving 7 bytes

(a,b,c)=>[b%10*1e3+c*10+a/1e3|0,a/10%100%12|0||12,b/10|0+a%10*10]

Try it online!

Straight modular arithmetic. Receives 3 integers (Y,M,D) and returns an array of 3 integers ([Y,M,D])

\$\endgroup\$
1
  • \$\begingroup\$ (a,b,c,T=10)=>[b%T*1e3+c*T+a/1e3|0,a/T%100%12|0||12,b/T|0+a%T*T] \$\endgroup\$
    – tsh
    Jan 8, 2019 at 5:51
1
\$\begingroup\$

Python 3, 126 111 bytes

Input and output as a list of strings. Probably could be shorter if I can rewrite this as a lambda.

def f(d):d=d[0][1:]+d[1].zfill(2)+d[2].zfill(2)+d[0][0];return[d[4:],str((int(d[:2])-1)%12+1),str(int(d[2:4]))]

Try it online!

\$\endgroup\$
1
\$\begingroup\$

Retina 0.8.2, 78 bytes

,(.\b)?
$#1$*0$1
(.)(..)(..)(...)
$4$1;11$*1$2$*1,$3$*
;(1{12})*
,1
,(1*)
,$.1

Try it online! Link includes test cases. Explanation:

,(.\b)?
$#1$*0$1

Replace the commas with zeros or just delete them for 2-digit numbers.

(.)(..)(..)(...)
$4$1;11$*1$2$*1,$3$*

Rearrange the year and extract the mis-decoded month and day in unary, adding 11 to the month.

;(1{12})*
,1

Reduce the month modulo 12 and add 1, bringing it into the desired range.

,(1*)
,$.1

Convert the month and day back to decimal without leading zeros.

\$\endgroup\$
1
\$\begingroup\$

Jelly,  19  18 bytes

-1 thanks to Erik the Outgolfer (D¹ŻṖ?d⁵DẎ)

d⁵DẎ€Ẏṙ5ṁƲḌṃ2¦12Ṫ€

A monadic link accepting a list of integers which yields a list of integers.

Try it online! Or see the test-suite.

How?

d⁵DẎ€Ẏṙ5ṁƲḌṃ2¦12Ṫ€ - Link: list of integers, dt     e.g. [        1779,        3,        14]
d⁵                 - divmod 10 (vectorises)              [      [177,9],    [0,3],     [1,4]]
  D                - to decimal digits                   [[[1,7,7],[9]],[[0],[3]],[[1],[4]]]]
   Ẏ€              - tighten €ach:                       [    [1,7,7,9],    [0,3],     [1,4]]
         Ʋ         - last four links as a monad (call that x):
     Ẏ             -   tighten x                         [     1,7,7,9,      0,3,       1,4]
       5           -   literal five
      ṙ            -   rotate (left) left by (right)     [     3,1,4,1,      7,7,       9,0]
        ṁ          -   mould like x                      [    [3,1,4,1],    [7,7],     [9,0]]
          Ḍ        - from decimal digits                 [         3141,       77,       90]
             ¦     - sparse application: {
            2      -   to indices: literal two                                 77
           ṃ  12   -   do: base decompress using [1..12]                    [6,5]
                   - }                                   [         3141,    [6,5],       90]
                Ṫ€ - tail €ach                           [         3141,       5,        90]
\$\endgroup\$
3
  • \$\begingroup\$ D¹ŻṖ?d⁵DẎ. \$\endgroup\$ Jan 7, 2019 at 23:09
  • \$\begingroup\$ Very smart, thanks! \$\endgroup\$ Jan 8, 2019 at 0:34
  • \$\begingroup\$ It's really not very smart; d⁵ is a usual way to add a leading zero to a one-digit number's decimal representation, when dealing with two-digit numbers. DẎ just extends this to >2-digit numbers, so that they're converted to their decimal representation properly (it's really D1¦Ẏ, since it only needs to cater for the first element of the divmod, but letting it cater for both doesn't harm). Finally, since only needs to be mapped, we just stick an after it and we're done. \$\endgroup\$ Jan 8, 2019 at 0:53
1
\$\begingroup\$

Japt, 46 42 32 27 bytes

-10 bytes thanks to fəˈnɛtɪk and -1 byte thanks to Shaggy

ùT2 ¬éJ ò4 vò c mn v_%CªCÃé

Try it online


Explanation:

ùT2 ¬éJ ò4 vò c mn v_%CªCÃé  // Full program
                             // Test input:                     [2008,9,16]
ù                            // Left-pad each item
  2                          //   To length 2                   ["2008"," 9","16"]
 T                           //   With "0"                      ["2008","09","16"]
   ¬                         // Join into a string               "20080916"
    éJ                       // Rotate counter-clockwise         "00809162"
       ò4                    // Cut into slices of length 4     ["0080","9162"]
          vò                 // Slice the first item into 2    [["00","80"],"9162"]
             c               // Flatten                         ["00","80","9162"]
               mn            // Cast each item into numbers     [0,80,9162]
                  v_         // Apply to the first item:        [0
                    %C       //   %12                           [0
                      ªC     //      ||12                       [12
                        Ã    // Escape v_                       [12,80,9162]
                         é   // Rotate clockwise                [9162,12,80]
\$\endgroup\$
2
  • 2
    \$\begingroup\$ Wish I had some time to work on this with you properly, looks like an interesting one. ù2'0 -> ùT2 for a quick saving, though. \$\endgroup\$
    – Shaggy
    Jan 7, 2019 at 17:23
  • \$\begingroup\$ Why do you need to do if x>12 return x%12||12 else return x. Can't you just do return x%12||12? \$\endgroup\$ Jan 7, 2019 at 18:55
0
\$\begingroup\$

05AB1E, 22 bytes

T‰JJ5._422S£εïNi12LÁsè

Try it online or verify all test cases.

Explanation:

T‰                       # Divmod each value in the (implicit) input with 10
                         #  i.e. [4291,8,0] → [[429,1],[0,8],[0,0]]
                         #  i.e. [2000,10,1] → [[200,0],[1,0],[0,1]]
  JJ                     # Then join everything together into a single string
                         #  i.e. [[429,1],[0,8],[0,0]] → "42910800"
                         #  i.e. [[200,0],[1,0],[0,1]] → "20001001"
    5._                  # Rotate it 5 times towards the left
                         #  i.e. "42910800" → "80042910"
                         #  i.e. "20001001" → "00120001"
       422S£             # Split it into parts of size 4,2,2
                         #  i.e. "80042910" → ["8004","29","10"]
                         #  i.e. "00120001" → ["0012","00","01"]
            ε            # Map each part to:
             ï           # Cast the string to an integer (removing leading zeros)
                         #  i.e. ["8004","29","10"] → [8004,29,10]
                         #  i.e. ["0012","00","01"] → [12,0,1]
              Ni         # And if the index is exactly 1:
                12L      # Push the list [1,2,3,4,5,6,7,8,9,10,11,12]
                   Á     # Rotate once towards the right: [12,1,2,3,4,5,6,7,8,9,10,11]
                    s    # Swap to get the map item
                     è   # And index it into the list (with automatic wraparound)
                         #  i.e. 0 → 12
                         #  i.e. 29 → 5
                         # (output the resulting list implicitly)
                         #  i.e. [8004,5,10]
                         #  i.e. [12,12,1]
\$\endgroup\$
0
\$\begingroup\$

Clojure, 178 bytes

An anonymous function that takes a sequence of integers (Y M D) as input.

#(let[s(apply format"%d%02d%02d"%)](let[[w x y z](map(fn[a](read-string(apply str\1\0\r a)))(partition 2(concat(rest s)[(first s)])))n(rem w 12)][(+(* 100 y)z)(if(= n 0)12 n)x]))

Try it online!

\$\endgroup\$
0
\$\begingroup\$

Pyth, 31 bytes

.e?tkb@S12tbvc.>sm.[\02`dQ3j46T

Try it online here, or verify all the test cases at once here.

.e?tkb@S12tbvc.>sm.[\02`dQ3j46T   Implicit: Q=eval(input()), T=10
                                    # Example input: [2008,9,16]
                 m       Q        Map each element of Q, as d, using:
                       `d           Stringify d
                  .[                Pad the above on the left...
                      2             ... to length of a multiple of 2...
                    \0              ... with "0"
                s                 Concatenate into a single string
                                    # '20080916'
              .>          3       Rotate 3 positions to the right
                                    # '91620080'
             c             j46T   Chop the above at indexes 4 and 6 (j46T -> 46 to base 10 -> [4,6])
                                    # ['9162', '00', '80']
            v                     Evaluate each element of the above as a numeric
                                    # [9162, 0, 80]
.e                                Map each element of the above, as b with index k, using:
  ?tk                               If k-1 is nonzero...
     b                              ... yield b, otherwise...
      @S12                          ... look up in [1-12]...
          tb                        ... element with index b-1 (modular indexing)
                                    # [9162, 12, 80]
                                  Implicit print result of previous map
\$\endgroup\$
0
\$\begingroup\$

Perl 6, 58 bytes

{m/(.)(..)(..)(...)/;$3~$0,$1%12||12,+$2}o*.fmt('%02d','')

Try it online!

Returns the year with leading zeros.

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.