Fit a word into an alphabet grid

55

8

Inspired by a meme I saw earlier today.

Challenge description

Consider an infinite alphabet grid:

ABCDEFGHIJKLMNOPQRSTUVWXYZ
ABCDEFGHIJKLMNOPQRSTUVWXYZ
ABCDEFGHIJKLMNOPQRSTUVWXYZ
ABCDEFGHIJKLMNOPQRSTUVWXYZ
ABCDEFGHIJKLMNOPQRSTUVWXYZ
...

Take a word (CODEGOLF in this example) and make it a subsequence of the grid, replacing unused letters by a space and removing letters at the end of the infinite grid altogether:

  C           O           
   DE G       O           
           L              
     F

Examples

STACKEXCHANGE

                  ST      
A C       K               
    E                  X  
  C    H                  
A            N            
      G                   
    E

ZYXWVUTSRQPONMLKJIHGFEDCBA

                         Z
                        Y 
                       X  
                      W   
                     V    
                    U     
                   T      
                  S       
                 R        
                Q         
               P          
              O           
             N            
            M             
           L              
          K               
         J                
        I                 
       H                  
      G                   
     F                    
    E                     
   D                      
  C                       
 B                        
A

F

     F

ANTIDISESTABLISHMENTARIANISM

A            N     T      
        I                 
   D    I         S       
    E             ST      
AB         L              
        I         S       
       H    M             
    E        N     T      
A                R        
        I                 
A            N            
        I         S       
            M

Notes

  • Trailing whitespaces are allowed.
  • You don't need to pad the last any line with spaces. For example, if the input is ABC, you may output just ABC without 23 trailing spaces.
  • You may assume input will match [A-Z]+ regex.
  • Alternatively, you may use lower-case alphabet, in which case output will match [a-z]+.
  • You must use a newline (\n, \r\n or equivalent) to separate lines, that is a list of strings is not a proper output format.
  • This is a challenge, so make your code as short as possible!

shooqie

Posted 2017-09-02T13:23:21.480

Reputation: 5 032

Are leading newlines allowed? – Erik the Outgolfer – 2017-09-02T13:46:11.430

@EriktheOutgolfer Sure, as long as it doesn't mess up grid structure. – shooqie – 2017-09-02T13:49:57.173

Would it be okay if a non-fatal error stops the program? – Zacharý – 2017-09-02T21:07:20.710

@Zacharý Although I can see how that could save some bytes, I think it's ugly and produces undesired, superfluous output. So no. EDIT: Unless you can make your program non-fatally exit through an exit code or something that wouldn't print exception stack trace or something similar to stderr. – shooqie – 2017-09-02T21:09:41.317

Okay, my answer doesn't error. – Zacharý – 2017-09-02T21:16:26.060

list of strings is not a proper output format Do you mean the list containing each line, or any type of list of strings? This meta consensus states that a list of characters (i.e. each element is a single character) is a valid string, mainly because some languages lack such distinction. – JungHwan Min – 2017-09-03T00:47:34.270

@JungHwanMin Yeah, I realize that.By "list of lines" i mean specifically output like ["AB(...)", "(...)XYZ", "(...)"] – shooqie – 2017-09-03T15:04:45.273

7Suggested test case: BALLOON (two adjacent characters that are the same). – Kevin Cruijssen – 2017-09-04T12:37:08.067

Go the answer in PHP https://gist.github.com/elminson/37d3caa43033f901dd100386f7ae7bde

– Elminson De Oleo Baez – 2019-12-24T05:38:08.920

Answers

10

Husk, 15 bytes

TṪS`?' €…"AZ"ġ>

Try it online!

Explanation

TṪS`?' €…"AZ"ġ>  Implicit input, e.g. "HELLO"
             ġ>  Split into strictly increasing substrings: x = ["H","EL","LO"]
        …"AZ"    The uppercase alphabet (technically, the string "AZ" rangified).
 Ṫ               Outer product of the alphabet and x
  S`?' €         using this function:
                   Arguments: character, say c = 'L', and string, say s = "EL".
       €           1-based index of c in s, or 0 if not found: 2
  S`?'             If this is truthy, then c, else a space: 'L'
                 This gives, for each letter c of the alphabet,
                 a string of the same length as x,
                 containing c for those substrings that contain c,
                 and a space for others.
T                Transpose, implicitly print separated by newlines.

Zgarb

Posted 2017-09-02T13:23:21.480

Reputation: 39 083

7

Java 10, 161 159 152 bytes

s->{var x="";int p=0;for(var c:s)x+=p<(p=c)?c:";"+c;for(var y:x.split(";"))System.out.println("ABCDEFGHIJKLMNOPQRSTUVWXYZ".replaceAll("[^"+y+"]"," "));}

-2 bytes thanks to @Nevay.
-7 byte printing directly instead of returning a String, and converting to Java 10.

Explanation:"

Try it here.

s->{                      // Method with String parameter and no return-type
  var x="";               //  Temp-String
  int p=0;                //  Previous character (as integer), starting at 0
  for(var c:s)            //  Loop (1) over the characters of the input
    x+=p<(p=c)?           //   If the current character is later in the alphabet
                          //   (replace previous `p` with current `c` afterwards)
        c                 //    Append the current character to Temp-String `x`
       :                  //   Else:
        ";"+c;            //    Append a delimiter ";" + this character to Temp-String `x`
  for(var y:x.split(";")) //  Loop (2) over the String-parts
    System.out.println(   //   Print, with trailing new-line:
     "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
                          //    Take the alphabet,
        .replaceAll("[^"+y+"]"," "));}
                          //    and replace all letters not in the String-part with a space

The first part of the method splits the input-word into parts with a delimiter.
For example: CODEGOLFCO;DEGO;L;F or BALLOONB;AL;LO;O;N.

The second part loops over these parts, and uses the regex [^...] to replace everything that isn't matched with a space.
For example .replaceAll("[^CO]"," ") leaves the C, and O, and replaces everything else with a space.

Kevin Cruijssen

Posted 2017-09-02T13:23:21.480

Reputation: 67 575

1Wouldn't it be B;AL;LO;O;N? – NieDzejkob – 2017-09-04T12:59:47.843

1-2 bytes: for(char c:s)x+=p<(p=c)?c:";"+c;. – Nevay – 2017-09-04T13:24:45.610

6

C (gcc), 69 bytes

i;f(char*s){for(i=64;*s;putchar(*s^i?32:*s++))i+=i^90?1:puts("")-26;}

Try it online!

scottinet

Posted 2017-09-02T13:23:21.480

Reputation: 981

4

Perl 5, 44 bytes

40 bytes code + 4 for -lF.

print map/$F[0]/?shift@F:$",A..Z while@F

Try it online!

Dom Hastings

Posted 2017-09-02T13:23:21.480

Reputation: 16 415

The link you've posted is for 46 bytes version. – None – 2017-09-02T14:03:45.243

@ThePirateBay Thanks!! I knew I hadn't updated something! – Dom Hastings – 2017-09-02T14:06:07.257

4

Python 2, 92 bytes

f=lambda x,y=65:x and(y<=ord(x[0])and" "*(ord(x[0])-y)+x[0]+f(x[1:],-~ord(x[0]))or"\n"+f(x))

Try it online!

Halvard Hummel

Posted 2017-09-02T13:23:21.480

Reputation: 3 131

390 bytes – ovs – 2017-09-02T21:20:59.433

4

Japt, 18 16 bytes

-2 bytes thanks to @Shaggy

;ò¨ £B®kX ?S:Z
·

Uppercase input only.

Try it online!

Explanation

;

Switch to alternate variables, where B is the uppercase alphabet.

ò¨

Split the input string between characters where the first is greater than or equal to (¨) the second.

£

Map each partition by the function, where X is the current partition.

Map each character in the uppercase alphabet to the following, with Z being the current letter.

kX

Remove all letters in the current partition from the current letter. If the current letter is contained in the current partition, this results in an empty string.

?S:Z

If that is truthy (not an empty string), return a space (S), otherwise return the current letter.

·

Join the result of the previous line with newlines and print the result.

Justin Mariner

Posted 2017-09-02T13:23:21.480

Reputation: 4 746

10 bytes for r"[^{Z}]"S seems a bit ridiculous, but I can't find any better way either... – ETHproductions – 2017-09-02T20:34:55.357

17 bytes – Shaggy – 2017-09-03T11:54:31.040

16 bytes – Shaggy – 2017-09-03T19:44:52.683

@Shaggy Good thinking with kX! – Justin Mariner – 2017-09-03T20:01:44.037

Actually I think you can change kX ?S:Z to oX ªS to save two bytes – ETHproductions – 2017-09-05T03:10:36.337

4

MATL, 24 23 bytes

''jt8+t1)wdh26X\Ys(26e!

Uses lowercase letters.

Try it at MATL Online!

Explanation

''     % Push empty string
jt     % Push input string. Duplicate
8+     % Add 8 to each char (ASCII code). This transforms 'a' 105,
       % 'b' into 106, which modulo 26 correspond to 1, 2 etc
t1)    % Duplicate. Get first entry
wd     % Swap. COnsecutive differences.
h      % Concatenate horizontally
26X\   % 1-based modulo 26. This gives a result from 1 to 26
Ys     % Cumulative sum
(      % Write values (converted into chars) at specified positions
       % of the initially empty string
26e    % Reshape into a 26-row char matrix, padding with char 0
!      % Transpose. Implicitly display. Char 0 is shown as space

Luis Mendo

Posted 2017-09-02T13:23:21.480

Reputation: 87 464

4

JavaScript (ES6), 79

Edit As a leading newline is accepted, I can save 2 bytes

s=>eval("for(o='',v=i=0;c=s.charCodeAt(i);v%=27)o+=v++?c-63-v?' ':s[i++]:`\n`")

For 1 byte more, I can accept lowercase or uppercase input:

s=>eval("for(o='',v=i=0;c=s[i];v%=27)o+=v++?parseInt(c,36)-8-v?' ':s[i++]:`\n`")

Less golfed

s=>{
  var i,o,c,v
  for(o = '', v = 1, i = 0; c = s.charCodeAt(i); v %= 27)
    o += v++ ? c-63-v ? ' ' : s[i++] : '\n'
  return o
}  

Test

f=s=>eval("for(o='',v=i=0;c=s.charCodeAt(i);v%=27)o+=v++?c-63-v?' ':s[i++]:`\n`")

function update() {
  var i=I.value
  i=i.replace(/[^A-Z]/gi,'').toUpperCase()
  O.textContent=f(i)
}

update()
<input id=I value='BALLOON' oninput='update()' >
<pre id=O></pre>

edc65

Posted 2017-09-02T13:23:21.480

Reputation: 31 086

You can replace the \n with a literal newline inside backticks for -1 byte. – Justin Mariner – 2017-09-02T20:41:29.797

@JustinMariner no I can't, not inside the double quote in eval – edc65 – 2017-09-02T20:48:17.467

Oh right, that's a shame. My bad. – Justin Mariner – 2017-09-02T20:49:11.163

3

Pyth, 18 bytes

#pbVGp?JqhzNNd=>zJ

Try it here.

Leading newline in output, lowercase alphabet.

Erik the Outgolfer

Posted 2017-09-02T13:23:21.480

Reputation: 38 134

3

Jelly, 19 bytes

<2\¬0;œṗfȯ⁶$¥€@€ØAY

Try it online!

Erik the Outgolfer

Posted 2017-09-02T13:23:21.480

Reputation: 38 134

OI<1®; -> >2\0; to save one byte (I actually did >2\0;œṗµØAf€ȯ€⁶µ€Y for 18 too, which I personally find easier to parse) – Jonathan Allan – 2017-09-03T00:32:13.113

@JonathanAllan I think that would fail for BALLOON or something. – Erik the Outgolfer – 2017-09-03T12:07:44.840

You are correct, yes - so it would required another byte with something like <2\1;¬; oh well. – Jonathan Allan – 2017-09-03T13:47:04.793

@JonathanAllan Anyways, I'll implement your idea in my answer...done. – Erik the Outgolfer – 2017-09-03T13:53:19.427

3

C (gcc), 91 63 bytes

-28 thanks to ASCII-only

_;f(char*s){for(_=64;*s;)putchar(++_>90?_=64,10:*s^_?32:*s++);}

Try it online!


Previous:

i,j;f(char*s){while(s[i]){for(j=65;j<91;j++)s[i]==j?putchar(s[i++]):printf(" ");puts("");}}

Yes, there's a shorter solution, but I noticed after I wrote this one... Try it online!

MD XF

Posted 2017-09-02T13:23:21.480

Reputation: 11 605

82 bytes, 80 if leading newline is allowed – ASCII-only – 2017-09-05T22:24:41.543

73 – ASCII-only – 2017-09-05T22:30:20.310

63 – ASCII-only – 2017-09-05T23:08:10.667

3

Mathematica, 101 bytes

StringRiffle[
  Alphabet[]/.#->" "&/@
   (Except[#|##,_String]&@@@
     Split[Characters@#,#==1&@*Order]),"
",""]&

Split the input into strictly increasing letter sequences, comparing adjacent letters with Order. If Order[x,y] == 1, then x precedes y in the alphabet and thus can appear on the same line.

For each sequence of letters, create a pattern to match strings Except for those letters; #|## is a shorthand for Alternatives. Replace letters of the Alphabet that match the pattern with spaces.


Illustration of the intermediate steps:

"codegolf";
Split[Characters@#,#==1&@*Order]  &@%
Except[#|##,_String]&@@@         #&@%
Alphabet[]/.#->" "&/@               %
{{"c", "o"}, {"d", "e", "g", "o"}, {"l"}, {"f"}}

{Except["c" | "c" | "o", _String], 
 Except["d" | "d" | "e" | "g" | "o", _String], 
 Except["l" | "l", _String],
 Except["f" | "f", _String]}

{{" "," ","c"," "," "," "," "," "," "," "," "," "," "," ","o"," "," "," "," "," "," "," "," "," "," "," "},
 {" "," "," ","d","e"," ","g"," "," "," "," "," "," "," ","o"," "," "," "," "," "," "," "," "," "," "," "},
 {" "," "," "," "," "," "," "," "," "," "," ","l"," "," "," "," "," "," "," "," "," "," "," "," "," "," "},
 {" "," "," "," "," ","f"," "," "," "," "," "," "," "," "," "," "," "," "," "," "," "," "," "," "," "," "}}

hftf

Posted 2017-09-02T13:23:21.480

Reputation: 436

2

Retina, 130 126 bytes

$
¶A
{-2=`
$'
}T`RL`_o`.$
+`(?<=(.)*)((.).*¶(?<-1>.)*(?(1)(?!)).+\3.*$)
 $2
(?<=(.)*)((.).*¶(?<-1>.)*(?<-1>\3.*$))
¶$2
}`¶.*$

Try it online! Edit: Saved 4 bytes by using @MartinEnder's alphabet generator. Explanation:

$
¶A
{-2=`
$'
}T`RL`_o`.$

Append the alphabet.

+`(?<=(.)*)((.).*¶(?<-1>.)*(?(1)(?!)).+\3.*$)
 $2

Align as many letters as possible with their position in the alphabet.

(?<=(.)*)((.).*¶(?<-1>.)*(?<-1>\3.*$))
¶$2

Start a new line before the first letter that could not be aligned.

}`¶.*$

Delete the alphabet, but then do everything over again until there are no misaligned letters.

Neil

Posted 2017-09-02T13:23:21.480

Reputation: 95 035

This seems to print only one line, not aligning letters on subsequent lines. – Justin Mariner – 2017-09-02T18:23:52.140

@JustinMariner My bad, I made a typo in my last golf and failed to check it properly. – Neil – 2017-09-02T19:29:12.367

2

05AB1E, 18 bytes

ćIgµ¶?AvDyÊið?ë¼?ć

Try it online!

Got trouble with 05AB1E ć (extract 1) leaving an empty string/list on the stack after the last element is extracted. This solution would be 1-2 bytes shorter if it weren't for that.

ćIgµ¶?AvDyÊið?ë¼?ć  Implicit input 
ć                   Extract the 1st char from the string
 Igµ                While counter != length of the string
    ¶?              Print a newline
      Av            For each letter of the lowercased alphabet
        DyÊ         Is the examined character different from the current letter?
           ið?      If true, then print a space

              ë¼?ć  Else increment the counter, print the letter and push
                    the next character of the string on the stack

scottinet

Posted 2017-09-02T13:23:21.480

Reputation: 981

Actually, ð, means "print a space and a newline". – Erik the Outgolfer – 2017-09-04T13:56:24.210

You're right. Fixed the code to actually print a newline. – scottinet – 2017-09-04T14:00:54.667

2

Golfscript, 22 21 bytes

Try it online!

-1 byte thanks to careful final redefining of the n built-in.

{.n>{}{'
'\}if:n}%:n;

Explanation (with a slightly different version):

{.n>{}{"\n"\}if:n}%:n; # Full program
{                }%    # Go through every character in the string
 .n>         if        # If ASCII code is greater than previous...
                       # (n means newline by default, so 1st char guaranteed to fit)
    {}                 # Do nothing
      {"\n"\}          # Else, put newline before character
               :n      # Redefine n as the last used character
                   :n; # The stack contents are printed at end of execution
                       # Literally followed by the variable n, usually newline
                       # So because n is by now an ASCII code...
                       # ...redefine n as the new string, and empty the stack

Josiah Winslow

Posted 2017-09-02T13:23:21.480

Reputation: 725

2

Retina, 80 bytes

^
;¶
{`;.*
¶;ABCDEFGHIJKLMNOPQRSTUVWXYZ
¶¶
¶
)+`;(.*)(.)(.*¶)\2
$.1$* $2;$3
;.*

Try it online!

There is always exactly one leading newline. The code somewhat clunkily prepends the word with the alphabet along with a marker (semicolon). It then moves the marker up to the first letter of the word, while changing all other letters it passes into spaces. It also removes the first letter of the word. It repeats this until the first letter of the word isn't after the marker anymore. Then it clears that marker and the rest of the alphabet, and replaces it with a new line and the alphabet with a marker again. It keeps repeating this until the input word is empty, then it cleans up the last alphabet and marker, leaving the desired output.

FryAmTheEggman

Posted 2017-09-02T13:23:21.480

Reputation: 16 206

2

q/kdb+, 48 45 bytes

Solution:

-1{@[26#" ";.Q.A?x;:;x]}@/:(0,(&)(<=':)x)_x:;

Try it online!

Note: Link is to a K (oK) port of this solution as there is no TIO for q/kdb+.

Examples:

q)-1{@[26#" ";.Q.A?x;:;x]}@/:(0,(&)(<=':)x)_x:"STACKEXCHANGE";
                  ST
A C       K
    E                  X
  C    H
A            N
      G
    E

q)-1{@[26#" ";.Q.A?x;:;x]}@/:(0,(&)(<=':)x)_x:"BALLOON";
 B
A          L
           L  O
              O
             N

Explanation:

Q is interpreted right-to-left. The solution is split into two parts. First split the string where the next character is less than or equal to the current:

"STACKEXCHANGE" -> "ST","ACK","EX","CH","AN","G","E"

Then take a string of 26 blanks, and apply the input to it at the indices where the input appears in the alphabet, and print to stdout.

"__________________________" -> __________________ST______

Breakdown:

-1{@[26#" ";.Q.A?x;:;x]}each(0,where (<=':)x) cut x:; / ungolfed solution
-1                                                  ; / print to stdout, swallow return value
                                                  x:  / store input as variable x
                                              cut     / cut slices x at these indices
                            (               )         / do this together
                                     (<=':)x          / is current char less-or-equal (<=) than each previous (':)?
                               where                  / indices where this is true
                             0,                       / prepended with 0
                        each                          / take each item and apply function to it
  {                    }                              / lambda function with x as implicit input
   @[      ;      ; ; ]                               / apply[variable;indices;function;arguments]
     26#" "                                           / 26 take " " is "      "...
            .Q.A?x                                    / lookup x in the uppercase alphabet, returns indice(s)
                   :                                  / assignment
                     x                                / the input to apply to these indices

Notes:

  • -3 bytes by replacing prev with the K4 version

streetster

Posted 2017-09-02T13:23:21.480

Reputation: 3 635

2

Powershell, 70 63 bytes

-7 bytes thanks @Veskah

$args|%{if($_-le$p){$x;rv x}
$x=("$x"|% *ht($_-65))+($p=$_)}
$x

Try it online!

Explanation:

For each character in the splatted argument:

  • Output string $x and clear $x value (rv is alias for Remove-Variable), if a code of the current character less or equivalent (-le) to a code of the previous character.
  • Append spaces and the current character to $x, store it to $x. Also it freshes a previous character value.

Output last $x.

mazzy

Posted 2017-09-02T13:23:21.480

Reputation: 4 832

163 Bytes using splatting. Tried to use |% *ht to save some bytes but looks like it broke even. – Veskah – 2019-10-09T17:10:14.670

1

Jelly, 24 21 bytes

3 bytes thanks to Erik the Outgolfer.

O64;I%26’⁶ẋЀ;"⁸Ẏs26Y

Try it online!

Leaky Nun

Posted 2017-09-02T13:23:21.480

Reputation: 45 011

8I believe this fails for input "BALLOON" - the repeated characters are on the same line. – Justin Mariner – 2017-09-02T18:03:21.380

1

SOGL V0.12, 22 bytes

±E⁄Z*{@;eJι=?Xē}}¹∑z⁄n

Try it Here!

dzaima

Posted 2017-09-02T13:23:21.480

Reputation: 19 048

1

JavaScript (ES6), 87 bytes

f=([...s])=>s[0]?(g=i=>i>35?`
`+f(s):(i-parseInt(s[0],36)?" ":s.shift())+g(i+1))(10):""

Accepts uppercase or lowercase input. Output match the case of the input.

Tests

f=([...s])=>s[0]?(g=i=>i>35?`
`+f(s):(i-parseInt(s[0],36)?" ":s.shift())+g(i+1))(10):""

;O.innerText=["CODEGOLF","STACKEXCHANGE","F","ZYXWVUTSRQPONMLKJIHGFEDCBA","ANTIDISESTABLISHMENTARIANISM"]
.map(f).join("=".repeat(26)+"\n")
<pre id=O>

Justin Mariner

Posted 2017-09-02T13:23:21.480

Reputation: 4 746

1

Haskell, 81 74 73 bytes

q@(w:y)!(x:z)|w==x=x:y!z|1<2=min ' 'x:q!z
x!_=x
a=['A'..'Z']++'\n':a
(!a)

Saved 1 byte thanks to Laikoni!

Try it online.

Haskell Hugs optimizations

  1. The Hugs interpreter allows me to save one more byte by doing (!cycle$['A'..'Z']++"\n") instead of: (!cycle(['A'..'Z']++"\n")), but GHC does not like the former. (This is now obsolete; Laikoni already rewrote that line in a way that saved 1 byte.)

  2. Apparently, Hugs also does not require parentheses around the list pattern matcher, so I could save two more bytes going from: q@(w:y)!(x:z) to q@(w:y)!x:z.

Cristian Lupascu

Posted 2017-09-02T13:23:21.480

Reputation: 8 369

You can save a byte with a=['A'..'Z']++'\n':a;(!a). Interesting to now that Hugs seems to have somewhat laxer rules. – Laikoni – 2017-09-02T20:06:52.130

@Laikoni I'm looking at Haskell for months now and it doesn't cease to amaze me. I love the a=...:a trick. Thanks! – Cristian Lupascu – 2017-09-03T06:32:46.730

I don't know if you are aware of this but I think its worth mentioning. The reason Hugs is different here is that there is lower operator precedence for user defined operators than in the ghc. – Post Rock Garf Hunter – 2017-09-03T14:05:29.580

@WheatWizard I wasn't aware. This makes perfect sense, given the error I got in GHC. – Cristian Lupascu – 2017-09-03T17:32:55.320

1

R, 129 117 bytes

function(s){z={}
y=diff(x<-utf8ToInt(s)-64)
z[diffinv(y+26*(y<0))+x[1]]=LETTERS[x]
z[is.na(z)]=" "
write(z,1,26,,"")}

Try it online!

Explanation (ungolfed):

function(s){
 z <- c()                  # initialize an empty vector
 x <- utf8ToInt(s)-64      # map to char code, map to range 1:26
 y <- diff(x)              # successive differences of x
 idx <- cumsum(c(          # indices into z: cumulative sum of:
    x[1],                  # first element of x
    ifelse(y<=0,y+26,y)))  # vectorized if: maps non-positive values to themselves + 26, positives to themselves
 z[idx] <- LETTERS[x]      # put letters at indices
 z[is.na(z)] <- " "        # replace NA with space
 write(z,"",26,,"")        # write z as a matrix to STDOUT ("") with 26 columns and empty separator.

Giuseppe

Posted 2017-09-02T13:23:21.480

Reputation: 21 077

1

Python 3, 87 85 bytes

def f(s,l=65):c,*t=s;o=ord(c)-l;return o<0and'\n'+f(s)or' '*o+c+(t and f(t,o-~l)or'')

Try it online!

Felipe Nardi Batista

Posted 2017-09-02T13:23:21.480

Reputation: 2 345

1

J, 39 bytes

(_65+3 u:[)}&(26{.'')/.~0+/\@,2>:/\3&u:

Try it online!

FrownyFrog

Posted 2017-09-02T13:23:21.480

Reputation: 3 112

1

Charcoal, 15 bytes

Fθ«J⌕αι⁺ⅉ‹⌕αιⅈι

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

 θ              Input string
F «             Loop over characters
     α     α    Uppercase letters predefined variable
      ι     ι   Current character
    ⌕     ⌕     Find index
             ⅈ  Current X co-ordinate
         ‹      Compare
        ⅉ       Current Y co-ordinate
       ⁺        Sum
   J            Jump to aboslute position
              ι Print current character

Neil

Posted 2017-09-02T13:23:21.480

Reputation: 95 035

1

APL (Dyalog Classic), 20 bytes

⊃¨⎕a∘.∩⍨⊢⊂⍨1,2≥/⎕a⍳⊢

Try it online!

ngn

Posted 2017-09-02T13:23:21.480

Reputation: 11 449

1

K (ngn/k), 29 28 bytes

{{x@x?`c$65+!26}'(&~>':x)_x}

Try it online!

{ } function with argument x

>':x for each char, is it greater than the previous char?

~ negate

& where (at which indices) do we have true

( )_x cut x at those indices, return a list of strings

{ }' for each of those strings

`c$65+!26

the English alphabet

x? find the index of the first occurrence of each letter in x, use 0N (a special "null" value) if not found

x@ index x with that; indexing with 0N returns " ", so we get a length-26 string in which the letters from x are at their alphabetical positions and everything else is spaces

ngn

Posted 2017-09-02T13:23:21.480

Reputation: 11 449

1

R, 95 bytes

Just run through the upper case alphabet repeatedly while advancing a counter by 1 if you encounter the letter in the counter position of the word and printing out the letter, a space otherwise.

function(s)while(F>""){for(l in LETTERS)cat("if"((F=substr(s,T,T))==l,{T=T+1;l}," "));cat("
")}

Try it online!

J.Doe

Posted 2017-09-02T13:23:21.480

Reputation: 2 379

1

GolfScript, 37 bytes

64:a;{.a>{}{'
'\64:a;}if.a-(' '*\:a}%

Try it online!

I did a Golfscript one under a different name, but it had incorrect output.

JosiahRyanW

Posted 2017-09-02T13:23:21.480

Reputation: 2 600

1

Ruby -n, 62 bytes

Scans the input string for sequences of increasing letters, and for each sequence, replace letters not in the sequence with spaces.

g=*?A..?Z
$_.scan(/#{g*??}?/){puts g.join.tr"^#$&"," "if$&[0]}

Try it online!

Value Ink

Posted 2017-09-02T13:23:21.480

Reputation: 10 608

0

Husk, 22 21 19 17 bytes

-2 bytes thanks to Zgarb (and a new language feature)

mȯΣẊṠ:ȯR' ←≠:'@ġ>

Try it online!

Explanation

               ġ>    Group into increasing sublists
mȯ                   To each sublist apply the following three functions
            :'@      ¹Append '@' (The character before 'A') to the start
   Ẋ                 ²Apply the following function to all adjacent pairs
           ≠            Take the difference of their codepoints
          ←             Minus 1
      ȯR'               Repeat ' ' that many times
    Ṡ:                  Append the second argument to the end.
  Σ                  ³concatenate

H.PWiz

Posted 2017-09-02T13:23:21.480

Reputation: 10 962

19 bytes with the new binary overloading of . – Zgarb – 2017-09-02T14:21:34.903

@Zgarb Wow fancy! – H.PWiz – 2017-09-02T14:23:43.260

0

Dyalog APL, 47 37 34 bytes

{↑{⍵∘{⍵∊⍺:⍵⋄' '}¨⎕A}¨⍵⊂⍨1,2≥/⎕A⍳⍵}

Try it online!

How? (argument is )

  • ⍵⊂⍨1,2≥/⎕A⍳⍵, split into alphabetically ordered segments
  • {...}¨, apply this function to each letter (argument is ):
    • ⎕A, the alphabet
    • ...¨, apply this function to each argument (argument is ):
      • ⍵∘, pass in as the left argument () to the function:
        • {⍵∊⍺:⍵⋄' '}, if is in , then return , otherwise a space. This function is what creates a line of text.
  • , turn into an array (equivalent of adding the newlines)

Zacharý

Posted 2017-09-02T13:23:21.480

Reputation: 5 710

0

Mathematica, 73 71 72 bytes

Print@@(Alphabet[]/.Except[#|##,_String]->" ")&@@@Split[#,Order@##>0&];&
(* or *)
Print@@@Outer[If[!FreeQ@##,#2," "]&,Split[#,Order@##>0&],Alphabet[],1];&

sacrificed a byte to fix the output

Takes a list of lower case characters (which is a "string" per meta consensus).

Try it on Wolfram Sandbox

Usage

f = (Print@@(Alphabet[]/.Except[#|##,_String]->" ")&@@@Split[#,Order@##>0&];&)

 

f[{"c", "o", "d", "e", "g", "o", "l", "f"}]
 c           o           
  de g       o           
          l              
    f                    

JungHwan Min

Posted 2017-09-02T13:23:21.480

Reputation: 13 290

2Your input is a list of strings? Is this valid? – None – 2017-09-03T00:00:23.417

1Also this outputs {Null, Null, Null, Null} at the end. Is this allowed by OP? – None – 2017-09-03T00:16:14.853

@BillSteihn Yes, per meta consensus. For your second question, it prints the string to STDOUT. The Nulls are what the expression evaluates to, not a part of STDOUT (you can see this easily on Mathematica Kernel). For now, I fixed the issue by adding a byte.

– JungHwan Min – 2017-09-03T00:26:31.893

@BillSteihn the question specifies that a list of strings (i presume the list containing each line) is not a valid output format. I reckon it's fine as the input format, especially if it's a list of characters (plus, some languages have no distinction between a string and a list of characters, so disallowing this only makes the question unfair). – JungHwan Min – 2017-09-03T00:42:23.527

0

><>, 63 bytes

d5*v
(?;\i:0
~{?\}::{::}@=::{$" ["a${=:}?$~@?$~o10d2*-{?$~{+}}?

Try it online!

Input is expected in uppercase.

Sok

Posted 2017-09-02T13:23:21.480

Reputation: 5 592

0

Kotlin, 133 131 129 bytes

fun r(s:String){var c=0
while(0<1){('A'..'Z').map{if(c==s.length)return
if(s[c]==it){print(s[c])
c++}else print(" ")}
println()}}

Try it online!

Explained

fun r(s: String) {
    // Current character
    var c = 0
    // Keep going until the end of the string
    while (0 < 1) {
        // Go through the letters
        ('A'..'Z').map{
            // If the word is done then stop
            // Have to check after each letter
            if (c == s.length) return
            // If we are at the right letter
            if (s[c] == it) {
                // Print it
                print(s[c])
                // Go to the next letter
                c++
            // Otherwise print space
            } else print(" ")
        }
        // Put a newline between the lines
        println()
    }
}

Test

fun main(args:Array<String>)=r("CODEGOLF")

Edit: Ran through my compressor, saved 2 bytes.

jrtapsell

Posted 2017-09-02T13:23:21.480

Reputation: 915

0

C++, 202 197 bytes

-5 bytes thanks to Zacharý

#include<iostream>
#include<string>
using c=std::string;void f(c s){std::cout<<c(s[0]-65,32)<<s[0];for(int i=1;i<s.size();++i)std::cout<<(s[i]>s[i-1]?c(s[i]-s[i-1]-1,32):"\n"+c(s[i]-65,32))<<s[i];}

HatsuPointerKun

Posted 2017-09-02T13:23:21.480

Reputation: 1 891

I think (s[i]>s[i-1])=>s[i]>s[i-1] works, along with moving the int i=1 to the for-loop. – Zacharý – 2017-09-09T14:27:26.617

Also, ("\n"+c(s[i]-65,32)) => "\n"+c(s[i]-65,32) – Zacharý – 2017-09-09T14:32:43.277

0

PHP, 121 bytes

<?$p=$argv[1];$b=substr;while($p){for($i=A;$i!=AA;$i++){if($p[0]==$i){echo$b($p,0,1);$p=$b($p,1);}else echo" ";}echo'
';}

Try it online!

Jo.

Posted 2017-09-02T13:23:21.480

Reputation: 974

0

Kotlin, 101 bytes

Port of the Powershell.

{s:String->var p=' '
var x=""
var r=""
s.map{c->if(c<p){r+=x+"\n";x=""}
x=x.padEnd(c-'A')+c
p=c}
r+x}

mazzy

Posted 2017-09-02T13:23:21.480

Reputation: 4 832

0

Rust, 163 bytes

|s:&str|{let mut s=s.bytes().peekable();while s.peek().is_some(){for c in 65..91{print!("{}",if Some(c)==s.peek().cloned(){s.next();c}else{32}as char)}println!()}}

Try it online!

Explanation

|s:&str|{                                        // Take a single parameter s (a string)
  let mut s=s.bytes().peekable();                // Turn s into a peekable iterator
  while s.peek().is_some(){                      // While s is nonempty:
    for c in 65..91{                             //   For every c in range [65, 91) (uppercase alphabet):
      print!("{}",if Some(c)==s.peek().cloned(){ //     If the next character in s is the same as c:
        s.next();                                //       Advance the iterator
        c                                        //       Print c as a character
      } else {                                   //     Else:  
        32                                       //       Print a space
      } as char)                                 //
    }                                            //
    println!()                                   //   Print a newline
  }
}

Herman L

Posted 2017-09-02T13:23:21.480

Reputation: 3 611

0

Stax, 12 bytes

ü→Δe-Y─▲99╣w

Run and debug it

Unpacked, ungolfed, and commented, it looks like this.

{<!}    block tests if one value is >= another
)       use block to split input into partitions by testing adjacent pairs
m       map partitions using rest of the program and output
  zs    put a zero-length array under the partition in the stack
  F     for each letter in the array, run the rest of the program
    65- subtract 65 (ascii code for 'A')
    _&  set the specified index to the character, extending the array if necessary

Run this one

recursive

Posted 2017-09-02T13:23:21.480

Reputation: 8 616

0

05AB1E, 21 19 17 bytes

Çü@0šÅ¡vð₂×yAykǝ,

Try it online!

Ç       push a list of ascii values of the input        [84, 69, 83, 84]
ü@      determine which letter is >= the next letter    [1, 0, 0]
0š      prepend a 0 (false) to that list                [0, 1, 0, 0]
Å¡      split input on true values                      [["T"], ["E", "S", "T"]]
v       for each list entry
  ð₂×     push 26 spaces
  y       push list entry (letters)
  Ayk     push the positions of that letters in the alphabet
  ǝ       replace characters c in string a with letters b
  ,       print the resulting string
        implicitly close for-loop

Dorian

Posted 2017-09-02T13:23:21.480

Reputation: 1 521

0

Two tied solutions:

Zsh, 71 bytes

for ((;#1;)){s=
for y ({A..Z})((#1==#y))&&s+=$y&&1=${1:1}||s+=\ 
<<<$s}

Try it online!

This uses straightforward comparison/ternary.

Zsh, 71 bytes

for ((;#1;)){s=
for y ({A..Z})s+=${${(M)1[1]%$y}:-\ }&&1=${1#$y}
<<<$s}

Try it online!

This is a bit more clever, appending to s either the matched letter or a space in one statement, then removing a letter if it matches from the front of $1.

GammaFunction

Posted 2017-09-02T13:23:21.480

Reputation: 2 838

-1

Mathematica, 184 bytes

(t=Characters@#;s=Flatten@Table[Alphabet[],(l=Length)@t];q=1;For[i=1,i<=l@s,i++,If[s[[i]]!=t[[q]],s[[i]]=" ",q++];If[q>l@t,q--;t[[q]]=0]];StringRiffle[StringPartition[""<>s,26],"\n"])&

J42161217

Posted 2017-09-02T13:23:21.480

Reputation: 15 931