Meta-bowling Golf

23

3

Your task is to create the shortest program (A) that outputs another program (B) with the most unique bytes, which in turn outputs the original program (A). Essentially, you are golfing one half of a pair of ouroboros programs (a.k.a. periodic iterating quine) and bowling the other half. A and B may be in different languages.

Rules and Scoring

Your final score is <number of unique bytes in B> / <number of bytes in A>. Highest score wins. It should be noted that the theoretical maximum score is 256.

  • Program A must be at least one byte long
  • Program B cannot consist entirely of no-ops, i.e. at least one character must affect the output in some way.
  • Standard rules of quines apply to both programs. Notably, error quines are not allowed in either case.

For the sake of answer format consistency, begin your answer with something like this:

# <Language for A> & <Language for B>, Score: <B score> / <A score> = <combined score>

Beefster

Posted 2019-02-14T17:37:49.290

Reputation: 6 651

In order for this to be clear I think you are going to have to clarify the second bullet point a little bit. What does it mean for a character to be a no-op exactly? – Post Rock Garf Hunter – 2019-02-14T17:48:51.847

By unique bytes, do you mean shared bytes, or similarity between the two? – KrystosTheOverlord – 2019-02-14T18:50:16.647

@KrystosTheOverlord, it would be simply within program B, with no relation to program A. For example, aaaaa has one unique byte and abcde has 5 unique bytes. – Beefster – 2019-02-14T18:52:27.180

@Beefster So, if I have a program abcde, would edcba count as original? I feel like I'm just being dumb, but I want to ask just in case – KrystosTheOverlord – 2019-02-14T18:54:52.217

@KrystosTheOverlord I think you're missing something. If Program A is abcde, then edcba is not also Program A. If Program B is abcde or edcba then either one would have 5 unique bytes. – Kamil Drakari – 2019-02-14T18:56:39.310

@KrystosTheOverlord both of those have 5 unique bytes. There is no requirement for originality. Both programs can technically be the same, but you'll have a maximum score of 1 that way. – Beefster – 2019-02-14T18:56:41.160

Am I right that you seem to be implying that multi-byte characters are not allowed in programme B? – Shaggy – 2019-02-14T19:41:36.360

@Shaggy. No. Multibyte characters are fair game, but you'd count it by individual bytes within the encoding. You could use a 16-bit encoding, UTF-8, or whatever floats your boat. – Beefster – 2019-02-14T19:45:42.230

Are both programs required to be in the same language? – Embodiment of Ignorance – 2019-02-14T20:17:20.667

@EmbodimentofIgnorance The question states "A and B may be in different languages." – Kamil Drakari – 2019-02-14T20:45:18.853

1I'm just waiting for the programs where program A is in unary or lenguage – Embodiment of Ignorance – 2019-02-14T22:01:35.190

4@EmbodimentofIgnorance Program A is scored in terms of number of bytes, not unique bytes. Lenguage/Unary would score horribly – Jo King – 2019-02-15T00:48:01.500

Oh, I read it wrong, I thought both programs were scored by unique bytes – Embodiment of Ignorance – 2019-02-15T03:22:23.660

This is definitely the most interesting challenge I've seen so far that has a bowling component. – dfeuer – 2019-03-17T08:20:42.387

Answers

14

Japt & Japt, Score: 255 / 38 = 6.71

Program A:

"iQ ²¯24
G²õ@i'#+Xd"iQ ²¯24
G²õ@i'#+Xd

Program B is over 8kB long, so long that the link breaks, so I won't paste the whole thing. Here's a sample:

#þ"iQ ²¯24
G²õ@i'#+Xd"iQ ²,#ÿ"iQ ²¯24
G²õ@i'#+Xd"iQ ²,#Ā"iQ ²¯24
G²õ@i'#+Xd"iQ ²

I couldn't find a way to get a NUL byte to work, which is why program B only has 255 unique characters. Program B essentially consists of 255 copies of a single program, where a single irrelevant byte is changed each time, and the first 254 executions are ignored.

For the explanation, I'll start with this simplified version of A so that the resulting B is easier to discuss.

"iQ ²¯23
3õ@i'#+Xd"iQ ²¯23
3õ@i'#+Xd

This program is based on the basic payload-capable Japt quine. The string at the start contains a duplicate of the rest of the program, iQ ² inserts a quote and duplicates to create a string representation of the entire program, and then ¯23 trims off itself and everything after it. The resulting string is a program that outputs Program A:

"iQ ²¯23
3õ@i'#+Xd"iQ ²

I will refer to this string as U.

The last line of A duplicates U a bunch of times with a small change each time. Specifically, for each number X in the range [1...3] it outputs "#c" + U where c is the character with charcode X. The default behavior of Japt is to output those strings with no quotation marks and separated by commas, so this is the output of our Simplified A (note that there's an unprintable byte between each # and "iQ:

#"iQ ²¯23
3õ@i'#+Xd"iQ ²,#"iQ ²¯23
3õ@i'#+Xd"iQ ²,#"iQ ²¯23
3õ@i'#+Xd"iQ ²

We'll call this Simplified B.

Simplified B has a simple structure, alternating between #c and U. Fortunately for this answer, each #c and U is treated as separated by a comma, and in this situation the behavior of that is everything except the very last U has no effect on the output. The only portion of Simplified B which affects the output is this:

"iQ ²¯23
3õ@i'#+Xd"iQ ²

Which is identical to U that we already know outputs Simplified A.

The only difference between Simplified A and Program A is that instead of generating copies for the range [1...3] the real program generates copies for the range [1...256]. That results in 256 versions of #c each of which has a different character, though the last version "Ā" is a multi-byte character so it doesn't add any unique bytes, but everything except the last U is still ignored.

Kamil Drakari

Posted 2019-02-14T17:37:49.290

Reputation: 3 461

Very nice :) Would this work for 38 bytes?

– Shaggy – 2019-02-14T19:12:41.857

@Shaggy The 27 needs to be tweaked whenever bytes are saved, but other than that it seems like it works. – Kamil Drakari – 2019-02-14T19:15:55.297

1@Shaggy The scoring is based on number of unique bytes in B, and there are only 256 possible bytes. As far as I'm aware, even the new version of B does not contain the Null byte. – Kamil Drakari – 2019-02-14T19:47:26.873

Tried a few things to get it working with the null byte, by the way, but all failed. – Shaggy – 2019-02-14T22:19:30.857

5

Program A, Gol><>, 256/20 bytes = 12.8

"44XFL|r2ssl3%Q4s]|H

Try it online!

Program B, Gol><>

"44XFL|r2ssl3%Q4s]|H	

 !"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~€‚ƒ„…†‡ˆ‰Š‹ŒŽ‘’“”•–—˜™š›œžŸ ¡¢£¤¥¦§¨©ª«¬­®¯°±²³´µ¶·¸¹º»¼½¾¿ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖ×ØÙÚÛÜÝÞßàáâãäåæçèéêëìíîïðñòóôõö÷øùúûüýþÿ

Try it online!

The program alternates between outputting itself followed by every byte and just outputting itself.

Explanation:

"            Wrapping string literal pushes the first line to the stack backwards
 44X         Push 256
    FL|      Push the range from 0 to 255
       r                  Reverse the stack
        2ss               Push a quote
           l3%            If the stack length is divisible by 3
              Q4s]|       Only take the top 20 characters
                   H      And output the stack

Jo King

Posted 2019-02-14T17:37:49.290

Reputation: 38 234

1

Program A: 05AB1E, score: 256/41 256/31 bytes = 8.258...

0"D34çý₅Ýç'q†22ǝ"D34çý₅Ýç'q†22ǝ

Try it online.

Program B: 05AB1E

0"D34çý₅Ýç'q†22ǝ"D34çýq 

 !"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnoprstuvwxyz{|}~ ¡¢£¤¥¦§¨©ª«¬­®¯°±²³´µ¶·¸¹º»¼½¾¿ÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖ×ØÙÚÛÜÝÞßàáâãäåæçèéêëìíîïðñòóôõö÷øùúûüýþÿÝç'q†22ǝ

Try it online.

Explanation:

The shortest for 05AB1E is this one: 0"D34çý"D34çý (14 bytes) provided by @OliverNi. My answer uses a modified version of that quine by adding ₅Ýç'q†vy27ǝD}J.

0            # Push a 0 to the stack
             #  STACK: [0]
 "D34çý₅Ýç'q†vDy27ǝ}J"
             # Push the string "D34çý₅Ýç'q†vDy27ǝ}J" to the stack
             #  STACK: [0,"D34çý₅Ýç'q†vDy27ǝ}J"]
  D          # Duplicate the string
             #  STACK: [0,"D34çý₅Ýç'q†vDy27ǝ}J","D34çý₅Ýç'q†vDy27ǝ}J"]
   34çý      # Join the stack by '"'
             #  STACK: ['0"D34çý₅Ýç'q†vDy27ǝ}J"D34çý₅Ýç'q†vy27ǝD}J']
₅Ý           # Push a list in the range [0,255]
  ç          # Convert each integer to an ASCII character
   'q†      '# Filter the "q" to the front
      22ǝ    # Insert it at index 22 in the string (replacing the second '₅')
             # (and output the result implicitly)

Program B will terminate as soon as it reaches the q, so the actual program B is:

0"D34çý₅Ýç'q†22ǝ"D34çýq

Everything after that is ignored, and the top of the stack (0"D34çý₅Ýç'q†22ǝ"D34çý₅Ýç'q†22ǝ) is output implicitly.

Kevin Cruijssen

Posted 2019-02-14T17:37:49.290

Reputation: 67 575