How to print the below format in the fewest bytes?

20

1

This challenge is inspired by this, now deleted question.


Take a positive integer N as input, and output a matrix with the numbers 1 .. N2 that follows the pattern below:

Fill in the first row with 1 .. N then fill the last row (row number N) with (N+1) .. 2N, then fill the second row with (2N+1) .. 3N and continue until you have filled all rows.

The output format is flexible, so list of lists etc. are accepted.

N = 1
1

N = 2
1  2
3  4

N = 3
1  2  3
7  8  9
4  5  6

N = 4
 1  2  3  4
 9 10 11 12
13 14 15 16
 5  6  7  8

N = 5
 1  2  3  4  5
11 12 13 14 15
21 22 23 24 25
16 17 18 19 20
 6  7  8  9 10

Standard rules apply. Shortest answer in bytes in each language wins. Explanations are encouraged as always.

Stewie Griffin

Posted 2018-03-01T07:47:06.543

Reputation: 43 471

Are entries allowed to terminate with an error, as long as that error is not printed to STDOUT? – Sok – 2018-03-01T10:14:37.750

@Sok yes, that's allowed by default. – Martin Ender – 2018-03-01T10:17:51.053

1I guess the title is taken from the deleted question, but as it's not very searchable (to find for dupe etc.), can you change to a better one? – user202729 – 2018-03-01T11:59:29.347

1Since "the output format is flexible", may I output a one-dimensional array with the numbers ordered from line to line? (ex: 1 2 3 7 8 9 4 5 6) Is the output format that flexible? – Olivier Grégoire – 2018-03-01T13:12:28.130

4The APL solution is probably a single character of Old Persian cuneiform. – Mark – 2018-03-02T02:38:30.440

Answers

7

05AB1E, 13 8 bytes

Saved 5 bytes thanks to Rod

nLô«āÉÏ

Try it online!

Explanation

n           # push input^2
 L          # push range [1 ... input^2]
  ô         # split into pieces each the size of the input
   «       # append the reverse of this 2D-list
     ā      # push range [1 ... len(list)]
      É     # check each element for oddness
       Ï    # keep only the elements in the 2D list which are true in this list

Emigna

Posted 2018-03-01T07:47:06.543

Reputation: 50 798

5

Ruby, 53 bytes

->n{r=*1..n*n;n.times{|x|p r.slice!(r[x*=n]?x:-n,n)}}

Explanation:

Put all the numbers into a single array first, then slice the array skipping a line for each iteration. After the first (n/2+n%2) iterations there is nothing left to skip, then get all the remaining lines backwards.

Try it online!

G B

Posted 2018-03-01T07:47:06.543

Reputation: 11 099

4

Python 2, 75 bytes

def f(n):a=range(n);print[[i*n-~j for j in a]for i in a[::2]+a[~(n%2)::-2]]

Try it online!

Shieru Asakoto

Posted 2018-03-01T07:47:06.543

Reputation: 4 445

4

JavaScript, 68 bytes

Edit 3 bytes saved, whetted by @user71546

First try, following the obvious route: count from 1 and fill the array from both sides, from outer to inner

n=>(v=0,q=[...Array(n)]).map((_,i)=>q[i&1?--n:i/2]=q.map(_=>++v))&&q

Test

var F=
n=>(v=0,q=[...Array(n)]).map((_,i)=>q[i&1?--n:i/2]=q.map(_=>++v))&&q

function test() {
  var n=+N.value;
  O.innerHTML = '<tr><td>'
  +F(n).map(r=>r.join('</td><td>')).join('</td></tr><tr><td>')
  +'</td></tr>'
}

test()
#O { margin: 1em }
td { text-align: right }
<input id=N type=number min=1 value=5 oninput='test()'>
<table id=O>

edc65

Posted 2018-03-01T07:47:06.543

Reputation: 31 086

370 bytes ;) – Shieru Asakoto – 2018-03-01T08:24:40.890

1@user71546 now 68 – edc65 – 2018-03-01T09:43:35.187

3

><>, 51+3=54 47 bytes

:&v
?!\1-:&:&*}}r:
 ~\
!~>1+::n&:&%:a84*@@?$~o?

Try it online!

Input is expected on top of the stack at program start using the -v flag. Output consists of non-aligned numbers separated by single spaces, and each line is separated by a single newline. Example output for N=5:

1 2 3 4 5
11 12 13 14 15
21 22 23 24 25
16 17 18 19 20
6 7 8 9 10

... followed by a single newline. Program terminates with an error (something smells fishy...), but that's on STDERR rather thatn STDOUT.

Explaination:

The first line simply stores a copy of N in the register.

The second line builds up the offset for each output row by subtracting 1 from N, multiplying this by N, rotating it to the bottom of the stack and then reversing the entire stack. When the number on top of the stack reaches 0, the stack should look like this (example uses N=5):

5 15 20 10 0 0

The third line discards the duplicate 0 from the top of the stack.

The fourth line increments the top of the stack and outputs a copy of it. This is then taken mod N, and this is used to decide if a space or newline should be printed, and if the top of the stack should be discarded - if last number printed is x, then x mod N == 0 indicates that the end of that output row has been reached. Execution ends when 1+ gets executed on an empty stack, throwing the termination error.

Previous version

This explicitly checked for an empty stack to end execution, and I was also including 3 bytes for the -v flag usage.

:&v
?!\1-:&:&*}}r:
 ~\
!;>1+::n&:&%:a84*@@?$~o?!~l?

Try it online!

Sok

Posted 2018-03-01T07:47:06.543

Reputation: 5 592

According to this meta, we no longer add flags to byte count so it is enough that you specify that the flag is used.

– Emigna – 2018-03-01T10:29:54.147

@Emigna O_O thank goodness for that! Thanks for the heads up – Sok – 2018-03-01T10:32:57.270

3

Haskell, 62 bytes

(0#)
m#n|m>=n^2=[]|k<-m+n=[m+1..k]:(k+n)#n++[[k+1..k+n]|k<n^2]

Try it online! Output is a list of lists, e.g. (0#) 3 yields [[1,2,3],[7,8,9],[4,5,6]].

Laikoni

Posted 2018-03-01T07:47:06.543

Reputation: 23 676

3

Perl 5, -p 52 51 bytes

#!/usr/bin/perl -p
map{$|--?$\="@0
".$\:say"@0";$_+=@0for@0}@0=1..$_}{

Try it online!

Ton Hospel

Posted 2018-03-01T07:47:06.543

Reputation: 14 114

2

JavaScript (ES6), 69 68 bytes

n=>[...Array(n)].map((_,i,a,j=((i*=2)<n?i:n+n+~i)*n)=>a.map(_=>++j))

Well it got outgolfed before I could post it but here it is anyway. Edit: Saved 1 byte thanks to @KevinCruijssen.

Neil

Posted 2018-03-01T07:47:06.543

Reputation: 95 035

n+n-i-1 can be n+n+~i for -1 byte, so then you are toe-to-toe with the other JavaScript answer again. :) – Kevin Cruijssen – 2018-03-01T12:33:16.230

@KevinCruijssen Brilliant thanks! – Neil – 2018-03-01T13:24:29.323

2

Java (OpenJDK 9), 101 bytes

n->{int x[][]=new int[n][n],i=0,j;for(;i<n;i++)for(j=0;j<n;)x[i%2<1?i/2:n+~i/2][j]=++j+i*n;return x;}

Try it online!

Credits

Olivier Grégoire

Posted 2018-03-01T07:47:06.543

Reputation: 10 647

1

You can save three bytes by changing the position of the j++: 102 bytes

– Kevin Cruijssen – 2018-03-01T12:34:50.563

1

And another byte changing n-i/2-1 to n+~i/2 101 bytes

– Kevin Cruijssen – 2018-03-01T12:36:48.653

@KevinCruijssen Thanks! I somehow posted the raw version, not the fully golfed one. My mistake, the first issue was tackled, but not the second. But you wrote them, so credits to you ;-) – Olivier Grégoire – 2018-03-01T13:04:24.887

Note: if somehow one-dimensional arrays are accepted, n->{int i=n*n,x[]=new int[i],r;for(;i-->0;x[(r%2<1?r/2:n+~r/2)*n+i%n]=i+1)r=i/n;return x;} – Olivier Grégoire – 2018-03-01T13:27:34.247

2

Jelly, 13 ... 6 bytes

Thanks JonathanAllan for -1 byte!

²sm0m2

Try it online!


Use an identical algorithm to the 05AB1E answer.

user202729

Posted 2018-03-01T07:47:06.543

Reputation: 14 620

Save a byte by removing R since s has implicit range of left.

– Jonathan Allan – 2018-03-02T18:37:49.400

2

R, 70 59 47 bytes

function(n)matrix(1:n^2,n,,T)[c(1:n,n:1)*!0:1,]

Try it online!

Thanks to Robin Ryder for a 4 byte golf, which I then golfed further.

Returns a matrix; constructs the matrix in sequence, e.g., [[1 2 3] [4 5 6] [7 8 9]], then rearranges the rows.

Giuseppe

Posted 2018-03-01T07:47:06.543

Reputation: 21 077

66 bytes by avoiding rbind. – Robin Ryder – 2019-05-08T11:18:59.557

@RobinRyder 59 bytes -- on mobile so I'll edit this in later

– Giuseppe – 2019-05-08T11:47:09.303

2

Jelly, 10 bytes

²ss2Ṛj@/Fs

Try it online!

How it works

²ss2Ṛj@/Fs  Main link. Argument: n

²           Square; yield n².
 s          Split; promote n² to [1, ..., n²] and split it into chuks of length n.
  s2        Split 2; generate all non-overlapping pairs of chunks.
            If n is odd, this leaves a singleton array at the end.
    Ṛ       Reverse the order.
     j@/    Reduce by join with reversed arguments.
            In each step, this places the first and second element of the next pair
            at the top and bottom of the accumulator.
        Fs  Flatten and split to restore the matrix shape.

Dennis

Posted 2018-03-01T07:47:06.543

Reputation: 196 637

2

Stax, 10 bytes

│æ╘▐⌡r▌═∟Y

Run and debug it online

The corresponding ascii representation of the same program is 12 characters.

JRx/r{]+rFmJ

Here's how it works.

JR              range [1 .. x^2] where x=input
  x/            split into subarrays of size x
    r           reverse
     {   F      for each subarray, execute block
      ]+r       concat array, and reverse result
          m     for each row, output ...
           J        each subarray joined by spaces

recursive

Posted 2018-03-01T07:47:06.543

Reputation: 8 616

1

Python 2, 72 68 63 bytes

-4 bytes thanks to Neil

def f(n):w=zip(*[iter(range(1,n*n+1))]*n);print(w+w[::-1])[::2]

Try it online!

Rod

Posted 2018-03-01T07:47:06.543

Reputation: 17 588

I assume you can save 4 bytes by eliminating the intermediate x variable? – Neil – 2018-03-01T12:23:47.030

1

C++ + Range V3, 159 bytes

#include<range/v3/all.hpp>
using namespace ranges::view;

[](int n){auto r=iota(1,n*n+1)|chunk(n);return concat(r|stride(2),r|reverse|drop(n%2)|stride(2));}

Live on Wandbox

Not counting the 2 newlines after using namespace range::view; they are just there to separate imports from the lambda.

Mildly interesting fact: this solution makes no heap allocations. It solves the problem in O(1) space.


Explanation:

  1. iota(1, n*n+1) -> [1 ... n*n]
  2. chunk(n): every n elements together, so [1 ... n] [n+1 ... 2*n] ...
  3. Call that r
  4. r | stride(2): take every other element: [1 ... n] [2*n+1...] ...
  5. concatenate that with:
  6. r | reverse | drop(n % 2): reverse, then drop the [1 ... n] term if n is odd (there'll be an odd number of rows and we only want to print the first term once). It seems like I should be able to just do r | reverse | take, but that doesn't work for some reason.
  7. stride(2) again, take every other element. This time it's in reverse.

More readable, and testable:

#include <range/v3/all.hpp>
using namespace ranges::view;

auto f(int n)
{
    auto rows = iota(1, n * n + 1)
        | chunk(n);
    return concat(
        rows | stride(2),
        rows
            | reverse
            | drop(n % 2)
            | stride(2));
}

#include <iostream>
int main(int argc, char** argv)
{
    std::cout << "N = " << argc << '\n';
    auto res = f(argc);

    for (auto const& row : res | bounded) {
        for (auto const& elem : row | bounded) {
            std::cout << elem << ' ';
        }
        std::cout << '\n';
    }
}

Justin

Posted 2018-03-01T07:47:06.543

Reputation: 19 757

O(log(n)) for storing the input, if measured in bit complexity. – user202729 – 2018-03-03T05:15:14.127

@user202729 Unsure what you mean. Are you saying that for an int n, I need log(n) bits to store the input? But that's the input anyway, and we are dealing with an int where sizeof(int) == 4 (most systems), so it's a constant number of bytes used regardless of the input. – Justin – 2018-03-03T05:28:45.233

1

Octave, 102 bytes

n=input('');A=B=vec2mat(1:n*n,n);i=j=0;do
B(++i,:)=A(++j,:);if++j<n
B(n-i+1,:)=A(j,:);end;until j>=n
B

Try it online!

Steadybox

Posted 2018-03-01T07:47:06.543

Reputation: 15 798

Nice! I didn't know Octave had an until command.And I didnt't know about vec2mat :( Unfortunately the same length: A=B=vec2mat(1:(n=input(''))*n,n) :( – Stewie Griffin – 2018-03-02T19:39:00.133

while j++<n is also exactly the same length... Have you tried the various options or are those just coincidences? – Stewie Griffin – 2018-03-02T19:51:15.860

@StewieGriffin In this case the while loop is the same length, I tried it both ways. Often do ... until is one byte shorter than while ... end, though. – Steadybox – 2018-03-02T19:52:19.570

1

C (gcc), 110 bytes

i,c,t,b;f(a,n)int*a;{for(b=n-1;i<n*n;t++,b--){for(c=0;c<n;)a[t*n+c++]=++i;for(c=0;c<n&i<n*n;)a[b*n+c++]=++i;}}

Try it online!

Fills out an array by alternating between 2 indices for rows: one index starting at the top and one starting at the bottom. The top row index starts at 0 and is incremented every 2 rows; the bottom row index starts at n-1 and is decremented every 2 rows.

Ungolfed:

void f(int* a, int n)
{
    //i = value to be written [1,n]; c = column index; t = top row index; b = bottom row index
    for(int i=1, c=0, t=0, b=n-1;
        i <= n*n; //when i = n*n, we have written all the values and we're done
        t++, b--) //t increments every 2 rows, b decrements every 2 rows
    {
        //write out 2 rows per loop

        //first row: fill out row at t
        for(c=0; c<n; c++, i++)
            a[t*n+c]=i;

        //second row: fill out row at b
        //this step will be skipped on the final loop for odd values of n, hence the (i<=n*n) test
        for(c=0; c<n && i<=n*n; c++, i++) 
            a[b*n+c]=i;
    }
}

vazt

Posted 2018-03-01T07:47:06.543

Reputation: 311

0

Jelly, 11 bytes

s2ZU2¦Ẏị²s$

Try it online!

Erik the Outgolfer

Posted 2018-03-01T07:47:06.543

Reputation: 38 134

0

CJam, 22 bytes

ri__*,:)/2/z[1W].{%:p}

Try it online!

Esolanging Fruit

Posted 2018-03-01T07:47:06.543

Reputation: 13 542

0

C (gcc) 80 78

I see now this solution is wrong

i;f(n){for(i=0;i++<n*n;printf("\n%3d"+!!(~-i%n),i>n?n+(i+n>n*n?i%n?:n:i):i));}

Try it online!

PrincePolka

Posted 2018-03-01T07:47:06.543

Reputation: 653

0

C (gcc), 36+8+61 = 105 bytes

compile with -Dp=printf("%d ",i),i++%n;);puts("") -Dq=i,n)

f(q{g(1,i);}g(q{for(;p;i<n*n&&h(q;}h(q{for(n+i<n*n&&g(n+q;p;}

Try it online!

attinat

Posted 2018-03-01T07:47:06.543

Reputation: 3 495