# Drum fill generator

Create a program that generates a drum fill. Your program will output a pattern of L (left hand hits), 'R' (right hand hits), and K for kick drum hits.

## Rules

• The pattern must never have more than 2 of the same hits consecutively.
• The pattern must be loopable, so it mustn't have more than 2 of the same hits when it loops.
• Your program accepts 1 argument which is the length of the pattern. You can assume this will always be an integer > 1.
• Program output must be random each time it's ran. It should be properly random each time, so that every combination is possible, so for an input of 2 for example: LR, LK, RL, RK, KL, KR all have a chance of being generated.
• IO can be used with any convenient method.
• Standard loopholes are forbidden.
• This is code-golf, so smallest program wins!

Example valid output:

RLRRKKLL
LRLLKKLR
LKKRLRKLRRKL
LRLR


Example invalid output:

LRLL // 3 characters when looped
LRLRRRLLR // 3 characters in a row
RRLRLLRR // 4 characters when looped

• No it should be properly random each time, so that every combination is possible, so for an input of 2: LL, LR, LK, RR, RL, RK, KK, KL, KR all have a chance of being generated. I'll add something to the rules about that now.
– TMH
Jan 6, 2020 at 17:08
• I've made those changes to the question, cheers!
– TMH
Jan 6, 2020 at 23:10
• May we output using three other distinct characters instead of L, R, K? (e.g. A, B, C or 2, 3, 9) Jan 6, 2020 at 23:13
• @tsh more than 2, not 2 or more.
Jan 7, 2020 at 6:19
• @tsh i'd make that $hits_{i+1\bmod n}$ and $hits_{i+2\bmod n}$, but yes.
Jan 7, 2020 at 6:35

# Jelly, 15 bytes

“LRK”ṗ;E3Ƥ$ÐṂX  A monadic Link accepting an integer which yields a list of characters. Try it online! ### How? Pretty similar to Nick Kennedy's Jelly answer... “LRK”ṗ;E3Ƥ$ÐṂX - Link: integer, n
“LRK”           - "LRK"
ṗ          - Cartesian power (all length n strings with alphabet "LRK")
ÐṂ  - keep those entries which are minimal under:
$- last two links as a monad: ; - concatenate with itself 3Ƥ - for each infix of length 3: E - all equal? X - random element  • ... but 1 byte shorter! Nice. Jan 6, 2020 at 23:21 # 05AB1E, 15 bytes …LRKãʒDJÅγà3‹}Ω  Try it online! …LRK # literal "LRK" ã # strings made of input of those letters ʒ } # filter: DJ # concatenate the string with itself Åγ # run-length encode à # maximum (largest run length) 3‹ # less than 3? Ω # get a random element  # R, 67 bytes n=scan();while(max(rle(c(x<-sample(c("L","R","K"),n,T),x))$l)>2)0;x


Try it online!

A full program taking an integer, n and implicitly printing the drum pattern.

• I didn't notice the clever use of pasting the values together to duplicate the vector so for a while thought it was possible to get something like LRLL. Very nicely done. Jan 8, 2020 at 19:26

# Jelly, 16 bytes

“LRK”ṗ;ŒɠṀ<ʋƇ3X


Try it online!

A monadic link taking the length $$\n\$$ and returning a Jelly string of the drum pattern. Like the other answers, assumes that $$\n > 1\$$

## Explanation

“LRK”ṗ           | Cartesian power of "LRK" and n
ʋƇ   | Keep those where the following is true:
;         | - Concatenate to itself
Œɠ       | - Lengths of runs
Ṁ      | - Max
<  3  | - Less than 3
X | Pick one at random


# Python 3, 115 $$\\cdots\$$ 112 104 bytes

from random import*
f=lambda n,s='L':any(b*3in s*3for b in'LRK')and f(n,''.join(choices('LRK',k=n)))or s


Try it online!

Saved a byte thanks to Chas Brown!!!
Saved 8 bytes thanks to Jonathan Allan!!!

• 112 bytes by using from random import* (a common trick). Jan 6, 2020 at 21:22
• Some improvements: 1. import*; 2. recursive lambda function; 3. multiply string (avoiding a space); 4. multiply by 3 (initial s='L' rather than s='LL'). 104 bytes Jan 6, 2020 at 21:24
• @ChasBrown Tried a few different imports but none of them saved any bytes -Thanks so much !! :-) Jan 6, 2020 at 21:30
• @JonathanAllan Totally amazing! Was trying to think of something recursive but didn't get anywhere. Also very clever changing over to s='L' and s*3! Thanks! :-) Jan 6, 2020 at 21:32

# APL (Dyalog Unicode), 30 bytesSBCS

Anonymous tacit prefix function.

{'LRK'[?⍺⍴3]}⍣{~1∊≢¨3∪/⍺,2↑⍺}⍨


Try it online!

{}⍨ apply the following function using the single argument also as left argument:

'LRK'[] index into the string "LRK" using the following indices:

⍺⍴3 reshape the number three into the length indicated by the left argument

? random indices in those ranges

⍣{} keep applying that function until the following is true:

2↑⍺ take the first two characters of the previously generated string

⍺, prepend the previously generated string

3∪/ the unique elements in each window of width three (lit, the union-reduction)

≢¨ the length of each set

1∊ is one a member thereof?

~ negate

# R, 75 bytes

?=diff;n=scan();while(!all(??c(x<-sample(9+c(2,3,9),n,T),x)))0;LETTERS[x]


Try it online!

Rejection sampling until an allowable pattern is found. Samples $$\x_i\$$ from the set $$\\{11, 12, 18\}\$$ (the positions in the alphabet of K, L, R). Agreeably, these numbers are such that a pattern is allowable iff $$\\forall i, (x_{i+1}-x_i)-(x_i-x_{i-1})\neq 0\$$. This condition is verified by calling diff twice (diff computes lagged differences, and here we want the lagged differences of the lagged differences).

• @NickKennedy Smart! I always forget about rle. You should post this separately IMO. Jan 7, 2020 at 6:20
• ok thanks! Have done so it Jan 7, 2020 at 8:03

# Ruby, 57 bytes

->x{0while /(.)\1\1/=~(w=(%w(L K R)*x).sample(x)*'')+w;w}


Try it online!

• You can save two sweet bytes by using ?redo:w instead of 0while +;w. See tio.run/… (I had come up with this answer before seeing yours, but it was too close and you got in first.) Jan 8, 2020 at 21:10

# JavaScript (ES6),  77  74 bytes

Assumes that the input is greater than $$\1\$$.

n=>(g=s=>s[n-1]?/(.)\1\1/.test(s+s)?g:s:g(s+'LRK'[Math.random()*3|0]))


Try it online!

# Charcoal, 26 bytes

Ｎθ≔KηＷ⊙KLR№×η³×κ³≔⭆θ‽KLRηη


Try it online! Link is to verbose version of code. Hangs for an input of 1 (could be changed to output a random hit at a cost of 1 byte). Explanation:

Ｎθ


Input the number of hits.

≔Kη


Initialise the output to an illegal value.

Ｗ⊙KLR№×η³×κ³


Repeat while the output is illegal, determined by tripling the output and each of the three letters K, L and R, and checking whether one contains any of the others.

≔⭆θ‽KLRη


Assign the desired number of randomly selected letters to the output.

η


Output the final legal result.

# Perl 5-pa, 86 bytes

$_=R x("@F"+2);1while s|(.)(?=\1\1)|(R,L,K)[rand 3]|e;s/..$//;($_.$_)=~/(.)\1\1/&&redo


Try it online!

# Ruby, 97 bytes

->x,y=->{[*1..x].map{%w[L R K].sample}}{a=y[];a=y[]while(a+a).chunk{|n|n}.any?{|_,e|e};a.join}


Try it online!

This is a lambda function, which takes the length input as x. It creates a function y which generates a list of length x containing random characters from the list ["L", "R", "K"]. It then checks to see if there are any repeating occurrences of more than 2, and if so recreates a random string.

The chunk method on an array groups consecutive elements.

I check for any repetitions on (a+a) (where a is the generated drum loop), to find any looping-round repetitions.

## Golfy Tricks

• Using e instead of e.size > 2 - this works as everything is truthy in Ruby except nil and false, and indexing out of bounds in an array returns nil.
• Using %w[L R K] instead of ["L","R","K"] or [?L,?R,?K] - This is ruby's whitespace-separated word array.

# Perl 6, 55 bytes

{({S:g{.}=<R L K>.pick}...{!/(.)$0$0/}o*x 2).tail}o\*x*


Try it online!

Anonymous code block that takes an integer and returns a string of RKLs.

### Explanation:

                                                  o\*x*  # Generate a string of n *s
{                                                }  # And pass to code block
(                     ...                 ).tail   # Get the last element of the sequence
{                   }      # Where each element is
S:g{.}=       # Substitute each character of the previous string with
<R K L>.pick   # A random character
{          }      # Until
o*x 2 # The double of the string
!                # Does not
/(.)$0$0/       # Contain three of the same character in a row


# Red, 141 112 bytes

func[n][until[s: copy""loop n[append s random/only"LRK"]parse
rejoin[s s][any[copy t skip opt t ahead not t]]]s]


Try it online!

# Burlesque, 43 bytes

pe"LRK"jCB{J?+gw)-]>]3.<}f[sa0#Rx/x/jrn-]!!


Try it online!

Made trickier by the fact there is no "select random element from list" as far as I am aware. 15 bytes are just trying to select a random element.

pe      # Push inputs onto stack takes "SEED N"
"LRK"   # Literal LRK
jCB     # Form all combinations of length N
{
J?+    # Double string
gw     # Zip with length of consecutive vals
)-]    # Take length
>]     # Maximum
3.<    # Less than 3
}f[     # Filter for
sa0     # Find number of matches
#Rx/x/j # Fiddle stack to get SEED 0 num_matches
rn      # Gen random ints
-]!!    # Select the first
`