53
\$\begingroup\$

Make a program that takes the word you input, and adds that word to the back of itself minus its first letter, then repeats until all letters are gone. For example, cat would become catatt, and hello would become helloellolloloo.

Input
Any of the 26 letters of the English alphabet. There may be multiple words separated by spaces, and the change should be applied to every word.

Output
The word(s) inputted, with each word put after itself with its first letter missing, and then with its second letter missing, and so on until there are no more letters to add.

More examples:

ill eel outputs illlll eelell

laser bat outputs laserasersererr batatt

darth vader outputs dartharthrththh vaderaderdererr

This is code golf, so the shortest code wins.

Clarification:
You can treat the input or output as a list. You can separate words using newline instead of space. You can add a trailing space to the input.

\$\endgroup\$
17
  • 24
    \$\begingroup\$ honestly, the multiple words thing is kinda annoying. All it does is require a split, apply the function on each word, and then join again. It's also quite debilitating for lots of esolangs which have to check for a space manually \$\endgroup\$
    – Jo King
    Sep 18, 2018 at 22:44
  • 5
    \$\begingroup\$ Can we take in input as a list of words and output as such? \$\endgroup\$
    – Quintec
    Sep 18, 2018 at 23:53
  • 5
    \$\begingroup\$ What length words do you need to handle? \$\endgroup\$
    – MickyT
    Sep 19, 2018 at 1:14
  • 6
    \$\begingroup\$ Is it OK for words to be separated by a newline in the output(instead of a space)? \$\endgroup\$
    – JayCe
    Sep 19, 2018 at 1:37
  • 11
    \$\begingroup\$ 1. Please update the spec with the new allowances (array I/O, trailing space, etc.) 2. Please inform the existing solutions in case any can save bytes by taking advantage of them. \$\endgroup\$
    – Shaggy
    Sep 19, 2018 at 8:36

74 Answers 74

2
\$\begingroup\$

C (gcc), 79 bytes

f(s,t)char*s,*t;{for(;*s;printf("%.*s",*s^32?t?t-s:~0:1,s),s++)t=strchr(s,32);}

Try it online!

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

Ruby, 42 bytes

->s{s.map{|a|(w=a.b).chars{a[0]='';w<<a}}}

Try it online!

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

JavaScript (Node.js), 33 bytes

s=>s.replace(/\B(?=(\S+))/g,"$1")

Try it online!

I don't really know JavaScript, but I just copied Arnauld's syntax with an idea I had for the regex substitution :P

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

Powershell, 29 23 bytes

Port of Javascript by @Arnauld

$args-replace'.',"$&$'"

Input and output are a list of word. Test script:

$f = {

$args-replace'.',"$&$'"

}

@(
    ,('illlll eelell', 'ill','eel')
    ,('laserasersererr batatt', 'laser','bat')
    ,('dartharthrththh vaderaderdererr', 'darth','vader')
) | % {
    $e,$s = $_
    $r = &$f @s
    $r = "$r"
    "$($r-eq$e): $r"
}

Output:

True: illlll eelell
True: laserasersererr batatt
True: dartharthrththh vaderaderdererr
\$\endgroup\$
2
\$\begingroup\$

Scala, 97 bytes

Scala main that takes a single String argument containing all the words.

args(0).split(" ").foreach(x=>{for(i<-0 to x.length)print(x.substring(i,x.length));print(" ")})

Try it online!

\$\endgroup\$
1
  • 1
    \$\begingroup\$ That's actually 95 bytes, if you remove the unnecessary newlines. \$\endgroup\$
    – Shikkou
    Sep 27, 2018 at 10:15
2
\$\begingroup\$

Perl 6, 44 32 bytes

-12 bytes thanks to nwellnhof!

~*.words>>.&{[~] $_,{S/.//}...0}

Try it online!

An anonymous Whatever lambda that takes a string and returns a string.

Explanation:

 *.words   # Split the given word by spaces
        >>.&{                  }  # Map each word to
                           ...  # A list composed of
                 $_              # The initial string
                   ,{S/.//}      # Remove the first character
                              0  # Until it's empty
             [~]   # All joined together
~   # Convert the list to a string, which joins by spaces
\$\endgroup\$
2
  • \$\begingroup\$ 29 bytes \$\endgroup\$
    – nwellnhof
    Sep 19, 2018 at 10:12
  • \$\begingroup\$ @nwellnhof I can't believe I forgot about .words! \$\endgroup\$
    – Jo King
    Sep 19, 2018 at 10:19
2
\$\begingroup\$

Python3, 58 bytes

Takes a space-separated string of words from stdin and returns stdout likewise.

f=lambda x:x and x+f(x[1:])
print(*map(f,input().split()))

It works by splitting the string into a list of words and using map() to call the recursive function f on each element. Honestly, I don't know exactly how f works. When the stack reaches the end of the word, x becomes the empty string (''), so the and statement returns False, which I suspect acts as the base case to end recursion.

Here's the same idea but without the functional aspects:

def f(x):
    return x and x + f(x[1:])

print(*( f(word) for word in input().split() ))
\$\endgroup\$
2
\$\begingroup\$

Java (JDK 10), 90 bytes

s->{var r="";for(var x:s){for(int i=0;i<x.length();)r+=x.substring(i++);r+=" ";}return r;}

Try it online!

Credits

  • -11 bytes thanks to Kevin Cruijssen, notifying me of the rule change about the input.
\$\endgroup\$
1
  • 1
    \$\begingroup\$ s.split(" ") can be just s. The rules have been changes, so you can take a String-array as input. (I also tried modifying the input array so you can remove the return-statement, but it seems to be longer.) \$\endgroup\$ Sep 19, 2018 at 13:28
2
\$\begingroup\$

Python3, 86 bytes

Reduced a lot, thanks to @ElPedro and @manatwork

def f(a):return a+f(a[1:])if''<a else'' 
for x in input().split():print(f(x),end=' ')

P.S. I tried removing split but then nothing is printing, its probably required in python3

\$\endgroup\$
8
  • \$\begingroup\$ The question asks for multiple words. Also, you should include your bytecount in the answer \$\endgroup\$
    – Jo King
    Sep 19, 2018 at 10:45
  • \$\begingroup\$ oh my bad will correct it \$\endgroup\$ Sep 19, 2018 at 10:46
  • \$\begingroup\$ Welcome to PPCG! You can use tryitonline to format your answer nicely and allow people to test it. See my answer as an example. \$\endgroup\$
    – ElPedro
    Sep 19, 2018 at 10:56
  • 1
    \$\begingroup\$ And TIO has a character counter too, which will say your solution currently has “106 chars, 106 bytes (UTF-8)”. BTW, unfortunately your code have a small glitch as for “cat” outputs “catat”, not “catatt”. Just change the condition to len(a)>0. Or to a>'' as it is shorter. Or to ''<a as that way you need no space between the if keyword and the expression. See Tips for golfing in Python. \$\endgroup\$
    – manatwork
    Sep 19, 2018 at 11:12
  • \$\begingroup\$ You don't need the space in the split(). Python splits on space by default. You can also remove the space in return '' to save another one. \$\endgroup\$
    – ElPedro
    Sep 19, 2018 at 11:14
2
\$\begingroup\$

Attache, 28 bytes

Join&sp##Sum@Suffixes=>Split

Try it online!

Alternatives

ReplaceF&(Sum@Suffixes)&/"\\w+"               ?? 31 bytes
ReplaceF«_,/"\\w+",Sum@Suffixes»              ?? 34 bytes, 32 chars
ReplaceF<~_,/"\\w+",Sum@Suffixes~>            ?? 34 bytes

Explanation

Join&sp##Sum@Suffixes=>Split    input, e.g.: "abc defg"
                       Split    split the input on spaces
                                e.g.: ["abc", "defg"]
                     =>         on each word:
                                  e.g.: "abc"
             Suffixes             take the suffixes of that word
                                  e.g.: ["abc", "bc", "c"]
         Sum@                     join them together
                                  e.g.: "abcbcc"
       ##                       then
Join&                           join the result by:
     sp                           spaces
\$\endgroup\$
2
\$\begingroup\$

MathGolf, 6 bytes

ÆÅ_╞↑ 

Try it online!

Outputs a trailing space, though you can add another byte to remove this.

Hopefully 6 bytes when implicit input is implemented. Yay.

Explanation:

        Implicit input
Æ       Implicit for loop over the next 5 instructions
 Å  ↑   While true without popping (empty string is false)
  _╞    Duplicate the top of stack and remove the first letter
        (space) Append a space to the stack
        Implicitly output the stack joined together
\$\endgroup\$
1
  • 1
    \$\begingroup\$ I can confirm that ÆÅ_╞↑ works in the latest version of MathGolf, with input ['Hello','world']. It is to be pushed today. I've worked on getting typed input and implicit input working properly, and now I can run the program above with correct output. \$\endgroup\$
    – maxb
    Sep 19, 2018 at 9:19
2
\$\begingroup\$

q 78 38 bytes

" "sv{r::x;{x,r::1_r}/[count x;x]}each
\$\endgroup\$
9
  • 2
    \$\begingroup\$ Welcome to PPCG! You can take input as a list of lines and return a list of lines rather than having to use vs and sv to split on whitespace. \$\endgroup\$
    – mkst
    Sep 19, 2018 at 21:11
  • \$\begingroup\$ Oh right, I thought the multiple words necessitated a string split, I`ll give it another go, thank you \$\endgroup\$
    – Thaufeki
    Sep 19, 2018 at 21:14
  • \$\begingroup\$ Also... take a look at the scan operator rather than recursing. \$\endgroup\$
    – mkst
    Sep 19, 2018 at 21:19
  • \$\begingroup\$ ... was thinking along the lines of { raze {1_x} scan x } each which can be golfed down a little more... \$\endgroup\$
    – mkst
    Sep 19, 2018 at 22:39
  • \$\begingroup\$ Used 'over' instead with some recursion, need to find a way to do it without globals \$\endgroup\$
    – Thaufeki
    Sep 19, 2018 at 23:27
2
\$\begingroup\$

Scala, 81 bytes

def e(s:List[String])=s.map(_.foldRight(("","")){(a,b)=>(a+b._1,a+b._1+b._2)}._2)

Try it online!

As per comments, this can receive and output a List[String]. This builds the output from right to left, starting with the rightmost letter, then prepending the two rightmost letters, and so on down the line.

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

Pascal (FPC), 129 bytes

var s:string;i,j:int32;begin read(s);repeat j:=Pos(' ',s);for i:=1to j do write(s[i..j-1]);write(' ');Delete(s,1,j)until s=''end.

Try it online!

Requires that the input ends in space, allowed in this comment.

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

Pyth, 8 6 bytes

m_s.__

Decreased byte(s?) thanks to @Steven H.

Try it online! Input and output are a list.

Expalanation:

        - implicit output
m       - map function d:
      _ -   ...d reversed...
    ._  -   ...get all prefixes of it...
  _s    -   ...joined and reversed
        - ...over implicit Q (input)
\$\endgroup\$
1
  • 1
    \$\begingroup\$ You can save a byte by using m instead of V, since that would make the Q implicit rather than explicit. \$\endgroup\$
    – Steven H.
    Sep 21, 2018 at 11:06
2
\$\begingroup\$

Twig, 73 bytes

Creates a macro with the function f() that receives an array of words, displaying the words separated by new lines.

{%macro f(a)%}{%for v in a%}{%for i in 0..v|length%}{{v[i:]}}{%endfor%}
{%endfor%}{%endmacro%}

To use it, just import:

{% import 'macro.twig' as a %}

{{ a.f(['a','sentence','is','a','list','of','words']) }}

{# to pass a string, you can split it #}
{{ a.f('a sentence is a list of words'|split(' ')) }}

You can try it on https://twigfiddle.com/8xech1
Warning: due to the way that output is handled in the link, I was forced to add a simple period (.) at the end of the line. This is NOT needed for normal operation.

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

Brachylog, 7 bytes

{a₁ᶠc}ᵐ

Try it online!

Explanation

{    }ᵐ          Map for each word:
 a₁ᶠ               Find all suffixes
    c              Concatenate into a single string
\$\endgroup\$
2
\$\begingroup\$

Haskell, 24 bytes

This solution is not optimal in two ways: 1) the other Haskell answer by nimi is 3 bytes shorter and 2) the input is limited to 9223372036854775807 characters (~36 exabytes), though I think it's an interesting find:

map.mconcat$drop<$>[0..]

Try it online! (sets a limit of 255 characters for TIO would time out otherwise)

Explanation

Since drop has type Int -> [a] -> [a] it forces [0..] to be [0..9223372036854775807] which is finite and thus the program terminates (eventually).

And mconcat takes the list of [drop 0, drop 1..] and gives us a function String -> String which is equivalent to:

\str-> drop 0 str ++ drop 1 str ++ .. ++ drop 9223372036854775807 str

Note: Once the argument of drop is greater or equal to the length of str it just appends empty strings.

Practical solution, 40 bytes

This won't take as long as the shorter solution but at a great cost of 16 bytes:

map$mconcat=<<map drop.zipWith pure[0..]

Try it online!

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

Burlesque, 8 bytes

{iS\[}ww

Try it online!

{
 iS # All suffixes
 \[ # Concatenate
}ww # For each word
\$\endgroup\$
2
\$\begingroup\$

APOL, 23 bytes

ƒ(s(i) j(ƒ(∋ V(⋒ ∈)))))

Explanation

ƒ(         List-builder for loop
  s(       String-split instruction (splits at spaces by default)
    i      Input
  )
  j(       String join instruction
    ƒ(     List-builder for loop
      ∋    For item (the current word being processed)
      V(   Substring instruction
        ⋒  For iterator (the thing the current for loop is iterating through, in this case the current word)
        ∈  For counter
      )
    )
  )
)
\$\endgroup\$
5
  • 1
    \$\begingroup\$ Given a quick read of the esolangs page (esolangs.org/wiki/APOL) and the corresponding interpreter, I do not think you can claim a score of 23 bytes. I do not see any implementation of an appropriate custom code page, which means the program actually deals with unicode characters. Correct me if I'm wrong, and somehow have missed this implementation detail, but it seems this would actually be 31 bytes. For reference, Jelly implements such a custom codepage, which you can read on here: github.com/DennisMitchell/jellylanguage/blob/master/jelly/… \$\endgroup\$ Dec 16, 2021 at 18:18
  • \$\begingroup\$ @ConorO'Brien I'm unsure how to do this. Could you explain how to do this? \$\endgroup\$
    – Ginger
    Dec 16, 2021 at 18:26
  • \$\begingroup\$ Sure. The reason why golfing languages can claim scores like that is because they have the ability to actually read the bytes of a file, and associate those bytes with particular characters. So, your interpreter has to be able to read a file of bytes, and index them into your desired unicode string, and then you can proceed as normal. Here's an example that should help: gist.github.com/ConorOBrien-Foxx/… . Note that you want to generate the raw file, e.g., with with open("sample.txt","wb") as f: f.write(b"\x10\x11"). \$\endgroup\$ Dec 16, 2021 at 18:36
  • \$\begingroup\$ You probably also want to have a way to convert your unicode to the byte values for ease of access of testing. Probably best done with command line arguments or perhaps as a REPL command \$\endgroup\$ Dec 16, 2021 at 18:37
  • 1
    \$\begingroup\$ @ConorO'Brien Okay, I've done it. \$\endgroup\$
    – Ginger
    Dec 16, 2021 at 20:14
2
\$\begingroup\$

Mathematica (Wolfram Language): 71 Characters

(a=Characters@#;StringJoin@Array[a[[#;;]] &,Length@a])&/@StringSplit[#]&

TIO Link

There pretty much has to be a better solution than this, but it works.

Explanation:

Takes a string and splits on spaces/newlines/punctuation, then iterates over this list. Finds a list of characters of each "word", then uses the Array to take all the elements, then all but the first, and so on. Then, these are joined (taking advantage of the fact that StringJoin ignores nested lists) and the function moves to the next word.

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

C#, 193 166 bytes

class a{static void Main(string[]b){foreach(var c in b)d(c,0);}static void d(string c,int e){if(e==c.Length)Console.Write(" ");else{Console.Write(c[e++..]);d(c,e);}}}

Try it Online!

Since .NET automatically splits the arguments at spaces, it's possible to loop over them without splitting them manually.
Other than that, this uses recursion to subtract one character at a time using the overload of string.Substring that takes only 1 argument which is the index to start at.

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

C (gcc), 94 bytes

f(char*s){char*e=s+strlen(s),*i=s;for(;i<e;*i++=*i-32?*i:0);for(i=s;i<e;i++)printf(*i?i:" ");}

Try it online!

Saves a pointer to the end of the string in char *e, then replaces spaces with null characters, then prints the string starting with each character and ending at the next null character, but printing a space if the current character is a null character.

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

JavaScript (Node.js), 88 bytes

f=s=>s.split(' ').map(e=>[...e].map((_,i,a)=>a.slice(i,a.length).join``).join``).join` `

Try it online!

\$\endgroup\$
3
  • \$\begingroup\$ By using flatMap you would save a join. \$\endgroup\$
    – tsh
    Sep 19, 2018 at 6:05
  • \$\begingroup\$ Welcome to PPCG. \$\endgroup\$
    – Shaggy
    Sep 19, 2018 at 6:58
  • \$\begingroup\$ @tsh throws error: flatMap is not a function tio.run/… \$\endgroup\$
    – user58120
    Sep 20, 2018 at 6:27
1
\$\begingroup\$

C (gcc), 64 bytes

f(s,t)char*s,*t;{for(;*s;t+=*s<33)for(strcpy(t,s++);*t&31;t++);}

Take two char* parameters: The first one for input, and the second one for output. The caller is responsible for malloc and free. Like most string functions in C, this one is designed to be vulnerable by overflow the buffer.

Try it online!

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

Gema, 24 characters

<L>=@x{$0}
x:?*=?*@x{$2}

Sample run:

bash-4.4$ gema '<L>=@x{$0};x:?*=?*@x{$2}' <<< 'darth vader'
dartharthrththh vaderaderdererr
\$\endgroup\$
3
  • \$\begingroup\$ I assume it's the same amount of bytes, unless there's multi-byte characters in there? \$\endgroup\$
    – Jo King
    Sep 19, 2018 at 8:33
  • \$\begingroup\$ Definitely the same. Gema doesn't use multi-byte characters. \$\endgroup\$
    – manatwork
    Sep 19, 2018 at 8:40
  • \$\begingroup\$ Okay. It was just strange that you used the term characters in the header \$\endgroup\$
    – Jo King
    Sep 19, 2018 at 8:47
1
\$\begingroup\$

Kotlin, 87 bytes

fun f(s:String):String=if(s=="")s else s.split(" ").joinToString(" "){it+f(it.drop(1))}
\$\endgroup\$
1
  • 1
    \$\begingroup\$ Hello and welcome to PPCG; nice first post. You could add a link to an online implementation (like TIO) for ease of verifying your solution. \$\endgroup\$ Sep 19, 2018 at 13:29
1
\$\begingroup\$

Python 2, 55 bytes

for x in input():
 y=""
 while x:y+=x;x=x[1:]
 print y,

Try it online!

Takes input as a list. output is separated by spaces.

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

Red, 67 66 bytes

func[s][foreach w split s" "[until[prin w take w tail? w]prin" "]]

Try it online!

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

Java, 131 bytes

char[]e(char[]a){int b=0,l=a.length,c,d=0;char[]n=new char[l*(l+1)/2];for(;b<l;b++){for(c=l-b;c>0;c--){n[d]=a[l-c];d++;}}return n;}

I know there is a better Java answer but, wanted to do it just with char arrays

char[] e(char[]a){
    int b=0,l=a.length,c,d=0;      //l to keep length, b for each iteration, c for each letter in iteration 
    char[] n= new char[l*(l+1)/2]; //Create new array with length based in triangular number sequence
    for(;b<l;b++) {
        for(c=l-b;c>0;c--) {
            n[d]=a[l-c];          //Fill it
            d++;                   //d keeps position in new array
        }
    }
    return n;
}
\$\endgroup\$
1
  • 1
    \$\begingroup\$ l+1 can most likely be -~l. \$\endgroup\$ Sep 19, 2018 at 16:02

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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