Playing with the musical turtle

20

2

My two kids like to play with the following toy:

Turtle

The colored areas with the shapes inside can be touched and the turtle then lights the area and plays a sound or says the name of the color or the shape inside. The middle button changes the mode. There is one mode in which the areas play different musical notes when touched, with a twist: if the kid touches three consecutive areas clockwise, a special melody 1 is played. If the three consecutive areas touched are placed counterclockwise, a special melody 2 is played.

The challenge

Let's simulate the internal logic of the toy. Given a string with 3 presses of the kid, return two distinct, coherent values if the three presses are for consecutive areas (clockwise or counterclockwise) and a third distinct value if they are not.

Details

  • The input areas will be named with a character each, which can be their color: ROYGB for red, orange, yellow, green and blue; or their shape: HSRTC for heart, square, star (R), triangle and circle. Case does not matter, you can choose to work with input and output just in uppercase or in lowercase.
  • The program will receive a string (or char array or anything equivalent) with three presses. Examples (using the colors): RBO, GYO, BBR, YRG, YGB, ORB...
  • The program will output three distinct, coherent values to represent the three possible outcomes: a first value if the combination does not trigger a special melody, a second value if the combination triggers the clockwise special melody, and a third value if the combination triggers the counterclockwise special melody. Example: 0 for no special combination, 1 for the melody triggered by a clockwise combination and -1 for the melody triggered by a counterclockwise combination.
  • You do not need to worry about handling wrong input.

Test cases

Input   Output      // Input based on colors
--------------
RBO     0           // No special combination
GYO     -1          // Counterclockwise melody triggered
BBR     0           // No special combination
YRG     0           // No special combination
YGB     1           // Clockwise melody triggered
ORB     -1          // Counterclockwise melody triggered
OOO     0           // No special combination
BRO     1           // Clockwise melody triggered

This is , so may the shortest code for each language win!

Charlie

Posted 2018-10-23T12:46:46.120

Reputation: 11 448

Is [0,0], [1,0], [0,1] allowed as output? I see the Mathematica answer doing that, and it would save 3 bytes in the 05AB1E answer. – Kevin Cruijssen – 2018-10-23T14:52:44.510

1@KevinCruijssen of course you can. The output values can be anything as long as they are distinct and consistent. – Charlie – 2018-10-23T14:55:35.290

Answers

12

Java 8, 48 39 33 bytes

s->"ROYGBRO BGYORBG".indexOf(s)|7

-6 bytes thanks to @RickHitchcock, so make sure to upvote him as well!

Takes uppercase color as input-String. Outputs -1 for none, 7 for clockwise, and 15 for counterclockwise.

Try it online.

Explanation:

s->      // Method with String parameter and integer return-type
   "ROYGBRO BGYORBG".indexOf(s)
         //  Get the index of the input in the String "ROYGBRO BGYORBG",
         //  which will result in -1 if the input is not a substring of this String
    |7   //  Then take a bitwise-OR 7 of this index, and return it as result

Old 39 bytes answer:

s->(char)"ROYGBRO BGYORBG".indexOf(s)/7

Takes uppercase color as input-String. Outputs 9362 for none, 0 for clockwise, and 1 for counterclockwise.

Try it online.

Explanation:

s->      // Method with String parameter and integer return-type
   (char)"ROYGBRO BGYORBG".indexOf(s)
         //  Get the index of the input in the String "ROYGBRO BGYORBG",
         //  which will result in -1 if the input is not a substring of this String
         //  And cast it to a char (-1 becomes character with unicode value 65535)
    /7   //  Integer-divide it by 7 (the char is implicitly converted to int doing so)

Kevin Cruijssen

Posted 2018-10-23T12:46:46.120

Reputation: 67 575

2I think 9632 is the best distinct and consistent value I've seen in these answers so far :) – Misha Lavrov – 2018-10-23T15:25:46.690

@MishaLavrov It could also be 10922 (integer-division by /6) or 8191 (integer-division by /8), but I choose /7 because it's the index of the space in the String. :) – Kevin Cruijssen – 2018-10-23T15:29:02.863

1@RickHitchcock Thanks! I thought I had tried some bitwise operations, but apparently not properly enough.. – Kevin Cruijssen – 2018-10-23T20:19:44.627

6

JavaScript (ES6), 41 bytes

Takes color initials as input. Returns 2 for none, true for clockwise or false for counterclockwise.

s=>~(x='ROYGBRO_ORBGYOR'.search(s))?x<5:2

Try it online!

Arnauld

Posted 2018-10-23T12:46:46.120

Reputation: 111 334

3At least an answer from Arnauld I can understand!! :) – Charlie – 2018-10-23T13:49:14.207

3@Charlie I think Arnauld is sick or something.. Not only is his answer readable and easy to understand, it's even longer than my Java answer! o.Ô Something is clearly wrong here. ;p – Kevin Cruijssen – 2018-10-23T15:34:17.463

s=>('ROYGBRO_ORBGYOR'.search(s)+8)/8|0 – l4m2 – 2018-10-23T16:01:07.513

1Do you even royg, bro? – Quentin – 2018-10-24T14:24:12.300

6

Python 2, 36 bytes

lambda i:'ROYGBRO ORBGYOR'.find(i)/7

-1 - None
0 - Clockwise
1 - Counterclockwise

Try it online!

Dead Possum

Posted 2018-10-23T12:46:46.120

Reputation: 3 256

Heh, great minds (or something)... https://codegolf.stackexchange.com/a/174635/53748 (if I'd seen this before trying stuff myself, I'd just have given you the byte save :p)

– Jonathan Allan – 2018-10-24T12:33:17.860

@JonathanAllan Don't worry, stuff happens :D I've upvoted your answer, as I can't dislike it! – Dead Possum – 2018-10-24T13:52:37.977

5

05AB1E, 15 11 bytes

Saved 4 bytes thanks to Kevin Cruijssen and Magic Octopus Urn.

Uses shapes.
Output [0, 0] for none, [1, 0] for clockwise and [0, 1] for counter-clockwise

‚.•ÌöJη•så

Try it online! or as a Test suite

Explanation

‚            # pair the input with its reverse
  .•ÌöJη•     # push the string "hsrtchs"
         så   # check if the input or its reverse is in this string

Emigna

Posted 2018-10-23T12:46:46.120

Reputation: 50 798

1Very similar as my 15-byte answer that I was about to post: .•1´₃éC•Â‚εXå}¥ resulting in [0], [1], or [-1], so +1 from me. Btw, I think (not sure) you can save three bytes by removing the last three, outputting [0, 0], [1, 0], and [0, 1] as distinct values. I see that the Mathematica answer does the same. Will ask OP for verification. – Kevin Cruijssen – 2018-10-23T14:52:08.837

Just asked OP, and you are indeed allowed to drop the last three bytes. As long as the three outputs are consistent and distinct it's fine whatever it is. – Kevin Cruijssen – 2018-10-23T14:56:13.817

2‚.•ÌöJη•så is 11 bytes if [1,0], [0,1] and [0,0] are considered unique (unless I'm missing something obvious here, adding ƶO to the end of that 11-byter is still 13 for the same 0, 1, 2 answer you have now). Test cases. Test cases 2. Order reversal removes the need for the loop. – Magic Octopus Urn – 2018-10-24T16:12:59.270

According to the comment on the original thread the 11-byter should be fine, as it uses 3 distinct values, you can beat Jelly with that one :). – Magic Octopus Urn – 2018-10-24T16:18:14.293

@KevinCruijssen Thank you! I always seem to think of unique as "single digit" for no reason :) – Emigna – 2018-10-26T08:11:28.880

@MagicOctopusUrn Thanks! I did try using  but somehow I ended up at 15 (or 13) with that as well. Great to see that someone managed better :) – Emigna – 2018-10-26T08:15:24.130

@Emigna if "better" means "tried switching argument order 60 different ways", sure :P. – Magic Octopus Urn – 2018-10-26T11:13:04.327

5

Excel, 29 bytes

=FIND(A1,"ROYGBRO_RBGYORB")<6

Uppercase colours as input.

Returns #VALUE! for no pattern, TRUE for clockwise, FALSE for anti-clockwise.

Can wrap in IFERROR( ,0) for +11 bytes to handle exception , and return '0' for no-pattern cases instead.

Wernisch

Posted 2018-10-23T12:46:46.120

Reputation: 2 534

4

Wolfram Language (Mathematica), 42 36 bytes

{"ROYGBRO","ORBGYOR"}~StringCount~#&

Try it online!

Counts the number of times the input appears in both "ROYGBRO" and "ORBGYOR". Returns {1,0} for clockwise, {0,1} for counterclockwise, and {0,0} for no special combination.

At the cost of only one more byte, we can get outputs of 0 for nothing, 1 for clockwise, and 2 for counterclockwise with "ROYGBRO.ORBGYORBGYOR"~StringCount~#&.

Misha Lavrov

Posted 2018-10-23T12:46:46.120

Reputation: 4 846

4

JavaScript (ES6), 32 bytes

s=>'ROYGBRO_ORBGYOR'.search(s)|7

Returns -1 if no combination, 15 if counterclockwise, 7 if clockwise.

let f =
s=>'ROYGBRO_ORBGYOR'.search(s)|7

console.log(f('RBO')) // -1
console.log(f('GYO')) // 15
console.log(f('BBR')) // -1
console.log(f('YRG')) // -1
console.log(f('YGB')) // 7
console.log(f('ORB')) // 15
console.log(f('OOO')) // -1
console.log(f('BRO')) // 7

Rick Hitchcock

Posted 2018-10-23T12:46:46.120

Reputation: 2 461

4

x86 machine code, 39 36 bytes

00000000: f30f 6f11 b800 0000 0066 0f3a 6310 0c89  ..o......f.:c...
00000010: c883 c807 c352 4f59 4742 524f 2042 4759  .....ROYGBRO BGY
00000020: 4f52 4247                                ORBG

Assembly:

section .text
	global func
func:					;the function uses fastcall conventions
					;no stack setup needed because we don't need to use stack
	movdqu xmm2,[ecx]		;Move DQword (16 bytes) from 1st arg to func(ecx) to SSE reg
	mov eax, msg			;Load address of constant str 'msg' into eax
	PcmpIstrI xmm2, [eax], 1100b	;Packed Compare String Return Index, get idx of [eax] in xmm2
	mov eax, ecx			;Move returned result into reg eax
	or eax, 7			;Bitwise OR eax with 7 to get consistent values
	ret				;return to caller, eax is the return register
section .data
	msg db 'ROYGBRO BGYORBG'

Try it online!

Output is 23 for none, 7 for clockwise, and 15 for counter-clockwise. Based on @RickHitchcock 's answer.

Saved 3 bytes by using an SSE string comparison instruction instead of using libc.

Logern

Posted 2018-10-23T12:46:46.120

Reputation: 845

1Can you count the machine code bytes here, since those bytes rely on the plafement of strstr in the binary? You can't just take those same bytes in another context and expect them to work the same. – Robert Fraser – 2018-10-24T04:55:42.330

There are pure machine code replacements that dont rely on the standard library https://www.strchr.com/strcmp_and_strlen_using_sse_4.2

– Robert Fraser – 2018-10-24T04:59:10.220

@RobertFraser The placement of the function is resolved during linking, the byte count will always be the same because the address of the function strstr will always be a 32-bit (4 byte) address. The machine code in my post is unlinked. – Logern – 2018-10-24T10:52:10.417

1I guess it's kind of a gray area. The function relies on data in the object file (linker map) before it can be used. But you could argue that's no different than a Java lambda needing a type declaration. – Robert Fraser – 2018-10-24T17:02:36.640

Note to be fully compliant with the ABI you'd have to use xmm5 or xmm6 which are caller-saved registers, instead of xmm2 which is callee-saved (but that shouldnt cost any bytes). – Robert Fraser – 2018-10-25T10:42:19.133

3

Python 2, 45 43 bytes

lambda i,a='ROYGBRO':(i in a)-(i[::-1]in a)

Try it online!

With ideas from and serious credit to @DeadPossum

-2 with thanks to @JoKing. Now outputs -1 = counterclockwise, 0 = none, 1 = clockwise.

My original effort is below for historical purposes.

Python 2, 52 51 bytes

lambda i,a='ROYGBRO':((0,1)[i[::-1]in a],2)[i in a]

Try it online!

0 = none, 1 = counterclockwise, 2 = clockwise

ElPedro

Posted 2018-10-23T12:46:46.120

Reputation: 5 301

45 bytes – Dead Possum – 2018-10-23T15:20:49.030

@DeadPossum That is seriously cool and different enough from mine for you to post as your own answer. I will upvote. – ElPedro – 2018-10-23T17:32:34.383

3

APL(Dyalog), 22 18 bytes

+/(⍷-⍷∘⌽)∘'ROYGBRO'

-4 bytes thanks to @ngn

Takes a string of color initials. Outputs 0 for no special pattern, -1 for counterclockwise, 1 for clockwise.

Try it online!

Quintec

Posted 2018-10-23T12:46:46.120

Reputation: 2 801

3

Perl 5 -p, 30 bytes

$_=ROYGBRO=~/$_/-ORBGYOR=~/$_/

Try it online!

Xcali

Posted 2018-10-23T12:46:46.120

Reputation: 7 671

3

Python 2,  35  36 bytes

+1 - for some reason I thought all buttons would be distinct >_<

Developed independently from what I have just seen (and now up-voted) by Dead Possum

lambda s:'ORBGYO.BROYGBR'.find(s)/7

Try it online!

Jonathan Allan

Posted 2018-10-23T12:46:46.120

Reputation: 67 804

I think you need to separate the strings of characters. This returns 0 (anti-clockwise) for "RBR," which isn't in your list of combinations. – Rick Hitchcock – 2018-10-24T13:36:35.323

@RickHitchcock ah I had assumed 3 different presses which is certainly incorrect. That'll make this effectively exactly the same as Dead Possum's! – Jonathan Allan – 2018-10-24T13:39:21.670

Can't delete from mobile... will delete or address later – Jonathan Allan – 2018-10-24T13:39:57.737

Yeah, it could be ambiguous, but one of the test cases ("OOO") shows that they could repeat. – Rick Hitchcock – 2018-10-24T13:41:08.580

@RickHitchcock yep that's what I saw after your comment - thanks! – Jonathan Allan – 2018-10-24T13:42:00.143

@RickHitchcock ...fixed it up by replacing the R with a . (which is what I actually had prior to "optimising" by use of a non-existent spec :p) – Jonathan Allan – 2018-10-24T14:53:16.007

2

Stax, 14 13 bytes

ù♀e▌d─█£F'♦O▬

Run and debug it

The output is

  • 1 for no special combination
  • 2 for counter-clockwise melody
  • 3 for clockwise melody

recursive

Posted 2018-10-23T12:46:46.120

Reputation: 8 616

2

Jelly, 12 bytes

,Ṛẇ€“¤ƈẎṬ%Ȥ»

Try it online!

-4 thanks to Jonathan Allan.

Clockwise: [1, 0]
Counter-clockwise: [0, 1]
Other: [0, 0]

Erik the Outgolfer

Posted 2018-10-23T12:46:46.120

Reputation: 38 134

@JonathanAllan Phew, thanks. Just saw again what I did, you were just 15 hours quicker. :P – Erik the Outgolfer – 2018-10-24T14:41:27.903

2

Pip, 19 bytes

Y"ROYGBRO"OaNyaNRVy

Outputs 10 for clockwise, 01 for counterclockwise, 00 for neither. Try it online!

Explanation

                     a is 1st cmdline argument
Y"ROYGBRO"           Yank that string into y variable
           aNy       Count of occurrences of a in y
          O          Output without newline
                RVy  y reversed
              aN     Count of occurrences of a in that string
                     Print (implicit)

DLosc

Posted 2018-10-23T12:46:46.120

Reputation: 21 213

2

J, 21 bytes

-&(OR@E.&'ROYGBRO')|.

Try it online!

How it works

-&(OR@E.&'ROYGBRO')|.  Monadic 2-verb hook. Input: a string.

                   |.  Map over [input string, input string reversed]:
      E.&'ROYGBRO'     Find exact matches of input in 'ROYGBRO'
  (OR@            )    Reduce with OR; is it a substring of 'ROYGBRO'?
-&                     Reduce with -; result is 1 for CW, -1 for CCW, 0 otherwise

Achieves maximum amount of function reuse.

Bubbler

Posted 2018-10-23T12:46:46.120

Reputation: 16 616

1

R, 38 bytes

grep(scan(,''),c('ROYGBRO','ORBGYOR'))

Try it online!

Returns :

  • No special combination : integer(0)
  • Counterclockwise melody triggered : 2
  • Clockwise melody triggered : 1

digEmAll

Posted 2018-10-23T12:46:46.120

Reputation: 4 599

1

Charcoal, 18 bytes

≔ROYGBROηI⁻№ηθ№⮌ηθ

Try it online! Link is to verbose version of code. Explanation:

 ROYGBRO            Literal string
≔       η           Assign to variable
            η   η   Value of variable
               ⮌    Reversed
             θ   θ  Input string
           №  №     Count matches
          ⁻         Subtract
         I          Cast to string
                    Implicitly print

Neil

Posted 2018-10-23T12:46:46.120

Reputation: 95 035

1

Common Lisp, 68 bytes

(defun x(s)(cond((search s "ROYGBRO")1)((search s "BGYORBG")-1)(0)))

Try it online!

JRowan

Posted 2018-10-23T12:46:46.120

Reputation: 231

1

Clean, 63 bytes

import StdEnv,Text
$s=map((>)0o indexOf s)["ROYGBRO","BGYORBG"]

Try it online!

[True, True] for no special noises, [True, False] for counterclockwise, [False, True] for clockwise.

Οurous

Posted 2018-10-23T12:46:46.120

Reputation: 7 916

0

Japt, 17 14 bytes

Takes the colours as input, in lowercase. Returns 0 for clockwise, 1 for counterclockwise or -1 if there's no combo.

`ygß`ê qÔbøU

Try it


Expanation

`...`            :Compressed string "roygbrow"
     ê           :Palindromise
       qÔ        :Split on "w"
         b       :Index of the first element
          ø      : That contains
           U     :  The input string

Shaggy

Posted 2018-10-23T12:46:46.120

Reputation: 24 623

0

Ruby, 53 36 bytes

->n{"\a\fDch+".index(""<<n%111)&./3}

Try it online!

Input: a 3-digit integer, where the digits represent colors:

  • 1 - red
  • 2 - orange
  • 3 - yellow
  • 4 - green
  • 5 - blue

Output:0 for clockwise, 1 for counterclockwise, nil otherwise.

G B

Posted 2018-10-23T12:46:46.120

Reputation: 11 099

0

C (gcc), 55 bytes

Returns 0 for none, -1 for CCW and 1 for CW.

f(char*s){s=!strstr("ORBGYOR",s)-!strstr("ROYGBRO",s);}

Try it online!

ErikF

Posted 2018-10-23T12:46:46.120

Reputation: 2 149