4
\$\begingroup\$

This question already has an answer here:

Your challenge is to output a Base64-encoded version of your source code, and optionally a line break. You must output the correct padding, if any. Standard quine rules apply, shortest answer wins.

It must be a valid RFC 4648 encoded base64 string, with no linebreaks (except optionally a trailing newline).

Test cases:

h -> aA==
PPCG! -> UFBDRyE=
Programming Puzzles and Code Golf -> UHJvZ3JhbW1pbmcgUHV6emxlcyBhbmQgQ29kZSBHb2xm

Base64 table

0   A   16  Q   32  g   48  w
1   B   17  R   33  h   49  x
2   C   18  S   34  i   50  y
3   D   19  T   35  j   51  z
4   E   20  U   36  k   52  0
5   F   21  V   37  l   53  1
6   G   22  W   38  m   54  2
7   H   23  X   39  n   55  3
8   I   24  Y   40  o   56  4
9   J   25  Z   41  p   57  5
10  K   26  a   42  q   58  6
11  L   27  b   43  r   59  7
12  M   28  c   44  s   60  8
13  N   29  d   45  t   61  9
14  O   30  e   46  u   62  +
15  P   31  f   47  v   63  /

If you want to test your submission, try base64encode.org.

\$\endgroup\$

marked as duplicate by pppery, Wheat Wizard code-golf Oct 18 at 13:56

This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.

  • 11
    \$\begingroup\$ codegolf.meta.stackexchange.com/a/8595/25180 \$\endgroup\$ – jimmy23013 Jul 16 '17 at 22:28
  • \$\begingroup\$ RFC 4648 mentiones two alphabets. Which one should we use? \$\endgroup\$ – Dennis Jul 16 '17 at 22:37
  • \$\begingroup\$ @Dennis the one in the table. \$\endgroup\$ – programmer5000 Jul 16 '17 at 22:37
  • \$\begingroup\$ WTB a language that outputs the letter of the given index 0->A = win. \$\endgroup\$ – Magic Octopus Urn Jul 17 '17 at 16:23
  • \$\begingroup\$ I've looked at this again after a few months and I still see this as clearly duplicate. All answers to the cryptiographic quine variant challenge work roughly by generating their own source and applying a built-in function to transform it to get its md5sum. Each of those answers could easily be rewritten to use a base64 builtin instead of a md5 built-in, without changing the core technique. I believe that counts as "little modification", making this challenge a duplicate. \$\endgroup\$ – pppery Oct 18 at 4:09
11
\$\begingroup\$

Bash, 27 bytes

trap -- 'trap|base64' EXIT

Based on this Bash quine. Note the trailing linefeed.

Try it online!

\$\endgroup\$
  • \$\begingroup\$ why do I obtain dHJhcCAtLSAndHJhcHxiYXNlNjQnIEVYSVQ= and dHJhcCAtLSAndHJhcHxiYXNlNjQnIEVYSVQK ? (last char diff) \$\endgroup\$ – V. Courtois Jul 17 '17 at 12:41
  • \$\begingroup\$ The program needs a trailing linefeed to be a valid base64 quine, which got removed by the syntax highlighter. \$\endgroup\$ – Dennis Jul 17 '17 at 14:22
  • \$\begingroup\$ I see ! Thanks. \$\endgroup\$ – V. Courtois Jul 17 '17 at 14:25
6
\$\begingroup\$

Javascript (ES6), 17 bytes

f=_=>btoa(`f=`+f)

I thought this solution would be obvious...

f=_=>btoa(`f=`+f)
console.log(f())
console.log(atob(f()))

\$\endgroup\$
4
\$\begingroup\$

Python, 133 112 bytes

from base64 import*;s=b'from base64 import*;s=%r;print(b64encode(s%%s).decode())';print(b64encode(s%s).decode())

Base64 representation:

ZnJvbSBiYXNlNjQgaW1wb3J0KjtzPWInZnJvbSBiYXNlNjQgaW1wb3J0KjtzPSVyO3ByaW50KGI2NGVuY29kZShzJSVzKS5kZWNvZGUoKSknO3ByaW50KGI2NGVuY29kZShzJXMpLmRlY29kZSgpKQ==

Try it online!

\$\endgroup\$
3
\$\begingroup\$

C (gcc), 342 bytes

f(a){putchar(a>61?43+a%2*4:a>51?a-4:a+65+a/26*6);}main(a){char*s="f(a){putchar(a>61?43+a%2*4:a>51?a-4:a+65+a/26*6);}main(a){char*s=%c%s%c,*t=malloc(342);for(sprintf(t,s,34,s,34);*t;f(*t%4*16+*++t/16),f(*t%16*4+*++t/64),f(*t++%64))f(*t/4);}",*t=malloc(342);for(sprintf(t,s,34,s,34);*t;f(*t%4*16+*++t/16),f(*t%16*4+*++t/64),f(*t++%64))f(*t/4);}

Try it online!

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

Mathematica, 108 bytes

Print[StringDelete[ExportString[StringJoin["Print[", ToString[#0, InputForm], "[]]"], "Base64"], "\n"] & []]

Full program. The spaces are necessary as part of the InputForm formatting. Output, note the trailing linefeed character:

UHJpbnRbU3RyaW5nRGVsZXRlW0V4cG9ydFN0cmluZ1tTdHJpbmdKb2luWyJQcmludFsiLCBUb1N0cmluZ1sjMCwgSW5wdXRGb3JtXSwgIltdXSJdLCAiQmFzZTY0Il0sICJcbiJdICYgW11d

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

Alice, 72 69 bytes

-3 bytes thanks to Martin Ender.

".w6+55*&w.q+!]k;9&wq4-!]kq&[d.t&w;q,ww].4%~4:k;28d3:&wq&[&]?ow4*+k@;

Base 64 representation:

Ii53Nis1NSomdy5xKyFdazs5JndxNC0hXWtxJltkLnQmdztxLHd3XS40JX40Oms7MjhkMzomd3EmWyZdP293NCora0A7

If anything, the base 64 representation looks less inscrutable than the original program.

Try it online!

Explanation

Since Alice has no base64 built-in, the vast majority of this program is a reduced implementation of base64. The quine framework prevents me from using ' to define constants in two bytes, but it also has some advantages. As luck would have it, the length of the source code is divisible by 3, and the characters >, ?, and ~ do not appear at the end of a 3-character block.

The first step is to create (most of) the base64 alphabet. The characters + and / do not appear in the base64 representation of the source code, so we do not need to handle them. This saves 9 bytes.

"      wrap the entire source code in a string and push each byte

.      copy ; from top of stack (i.e., push 59)
w      push return address (i.e., do the following twice)
6+     add 6 to the constant on the stack 
       this gives us 65 in the first iteration, and 71 in the second
55*w   do the following 26 times:
.q+    add tape position to constant
!      store at tape position
]      move tape right
k      return to pushed return address (end both loops)
;      remove constant from the stack, since it's no longer needed
9&w    do 10 times:
q4-    tape position minus 4
!      store at tape position
]      move tape right
k      repeat
q&[    return to position 0

Positions 0-61 on the tape are now filled with their base64 character equivalents. We now convert the source code to base 4.

d.     push stack depth (length of code excluding "), and put a useless copy below it
t&w    do that many times:
;      remove top of stack (copy of length on first iteration, 0 otherwise)
q,     move next byte to top of stack (using tape position as a register)
ww     do 4 times:
]      move tape forward (increase counter)
.      duplicate current byte or part thereof
4%     mod 4
~      swap: work with other copy
4:     divide by 4
k      repeat (end both loops)
;28    remove the excess 0 and push the base 4 representation of ",
       except that the first three base 4 digits are already in base 64

Finally, we convert from base 4 to base64 and output.

d3:&w  push return address once for each output character
q&[    move tape to position 0
&]     move tape to position corresponding to base 64 digit
?      get character from tape
o      output
w4*+   convert next base 64 digit (equivalent to 4*+4*+)
k      repeat until stack is empty
@      terminate
\$\endgroup\$
  • \$\begingroup\$ If you can save another byte elsewhere, could you shorten 6a*t by putting a ; at the end of the program and a . after the "? \$\endgroup\$ – Martin Ender Feb 26 '18 at 10:27
  • \$\begingroup\$ As it turns out, rearranging my base 4 -> base 64 conversion allowed me to save a third byte. \$\endgroup\$ – Nitrodon Feb 27 '18 at 1:16
1
\$\begingroup\$

Java 8, 202 bytes

v->{String s="v->{String s=%c%s%1$c;return java.util.Base64.getEncoder().encodeToString(s.format(s,34,s).getBytes());}";return java.util.Base64.getEncoder().encodeToString(s.format(s,34,s).getBytes());}

Explanation:

Try it online.

  • The String s contains the unformatted source code.
  • %s is used to input this String into itself with the s.format(...).
  • %c, %1$c and the 34 are used to format the double-quotes.
  • s.format(s,34,s) puts it all together.

And then java.util.Base64.getEncoder().encodeToString(....getBytes()) is used to encode the entire source code to a Base64-String.

Try it here with the Base64-encoding part removed to prove it's a quine.

\$\endgroup\$

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