# The rectangle spanned by two numbers

One way to generalize the concept of a range from the integers to the Gaussian integers (complex numbers with integer real and imaginary part) is taking all numbers contained in the rectangle enclosed by the two ends of the range. So the range between two Gaussian integers a+bi and c+di would be all Gaussian integers x+iy with min(a,c)<=x<=max(a,c) and min(b,d)<=y<=max(b,d).

For instance the range from 1-i to -1+2i would be the following set of numbers:

-1-i, -1, -1+i, -1+2i, -i, 0, i, 2i, 1-i, 1, 1+i, 1+2i

Your task is given two numbers a+bi and c+di to return the 2D range spanned by a+bi to c+di

## Examples

1       5      -> [1,2,3,4,5]
5       1      -> [5,4,3,2,1]
-1      -3     -> [-3,-2,-1]
1+i     1+i    -> [1+i]
1-i     -1+2i  -> [-1-i, -1, -1+i, -1+2i, -i, 0, i, 2i, 1-i, 1, 1+i, 1+2i]
1-i     2+i    -> [1-i, 1, 1+i, 2-i, 2, 2+i]
-2-i     -1+3i  -> [-2-i, -2, -2+i, -2+2i, -2+3i, -1-i, -1, -1+i, -1+2i, -1+3i, -i, 0, i, 0+2i, 0+3i, 1-i, 1, 1+i, 1+2i, 1+3i]


## Rules

• You can use pairs of integers to Input/Output Complex numbers
• The elements in the range can be sorted in any order
• Each element can only appear once in the range
• This is the shortest solution (per language) wins
• Presume that min(b,d)<=y<=max(d,d) is a typo and should actually read min(b,d)<=y<=max(b,d)? Aug 22, 2023 at 18:58
• @JosWoolley yes, I fixed it now Aug 22, 2023 at 19:00
• Last test case has numbers in the -2+iy range, which doesn't seem right considering the arguments given. Aug 22, 2023 at 19:29

# Vyxal, 2 bytes

ṡΠ


Try it Online!

ṡ  # Vectorised range
Π # Cartesian product


# J, 20 bytes

<.+"1[:(#:,@i.)1+|@-


Attempt This Online!

For positive integers x and y, i.(x,y) creates a matrix of

0      1        2        ... y-1
y      y+1      y+2      ... 2y-1
...
(x-1)y (x-1)y+1 (x-1)y+2 ... xy-1


Then (x,y)#: converts each number iy + j to a pair (i,j).

<.+"1[:(#:,@i.)1+|@-   Input: two pairs of integers
|@-   Elementwise absolute difference
,@i.           Create 2D range and flatten
#:               Base convert as described above
<.+"1                  Add elementwise minimum of two inputs to each row

• Excellent solution! Aug 23, 2023 at 16:30

# K (ngn/k), 18 bytes

++/(!1--)\(&;|)@\:


Try it online!

-1 thanks to ovs.

# K (ngn/k), 19 bytes

{+a+!1+(x|y)-a:x&y}


Try it online!

A function that takes two complex numbers as integer pairs x and y.

!(x,y) generates a two-row matrix whose columns are the cartesian pairs of 0..x and 0..y (excluding x and y).

• I think you made a typo in your explanation, there is no !(x,y) in your code Aug 23, 2023 at 8:37
• Not literally but effectively because the ! is applied to a pair.
– doug
Aug 23, 2023 at 8:39
• 18 as a fully tacit function: ++/(!1--)\(&;|)@\:
– ovs
Aug 23, 2023 at 9:54

# J, 47 bytes

The following dyad does the job, taking as left and right arguments the range edges:

   ([:>@,@{(<.<@:+i.@(+_1+2*0&<:)@:-~)/"1@,.)&.:+.


J uses ajb for denoting the number a+b*i, for instance:

   1j1 ([:>@,@{(<.<@:+i.@(+_1+2*0&<:)@:-~)/"1@,.)&.:+. 2j2
1j1 1j2 2j1 2j2


See this Demonstration on the J playground (press the "run" button on the upper right of the editor).

## Explanation

([:  >@,@{  (<.<@:+i.@(+_1+2*0&<:)@:-~) /"1@,.) &.:+.
__ _____  ___________________________ ___ __ _____: under complex decompose
cap  |      |                           |    \combine real and imag parts
|      |                           \insert verb in () in each row
|      \ verb creating boxed real/imag ranges (explained below)
\ open raveled Carthesian product between boxed coordinate ranges

<.  <@:+  i.@(+_1+2*0&<:)@:-~  fork; takes x, y and returns a boxed range.
___  ____  __ ____________  __
|    |     |  |             \_ difference between y and x
|    |     |  \_ adjust diff s.t. works for empty and reversed ranges
|    |     \_ range from 0 to y-1
|    \_ add min and range and box the result
\_ min of x and y

• 21 bytes Note rules allow you to use pairs of numbers for input, which turns out to be golfier than using J's complex numbers. Aug 22, 2023 at 19:44
• @Jonah, True, you should put it up as a solution! Aside of stretching I/O specs, your simplification of my "range" verb is beautiful (I never liked that ugly parenthesised blob in the middle) Aug 22, 2023 at 19:59

# Raku, 41 bytes

{($^x.re...$^y.re)X+(($x.im...$y.im)X*i)}


Try it online!

This anonymous function takes two complex numbers are arguments.

$^x.re ...$^y.re is the range of integers between the real parts of the arguments; ... is smart enough to make a decreasing range as appropriate. Similarly, $x.im ...$y.im is the range of integers between the imaginary parts of the arguments. X* i multiplies each element of the latter range by i, and X+ crosses the two ranges together with addition.

# Jelly, 3 bytes

rp/


A dyadic Link that accepts the two pairs of real and imaginary parts and yields a list of pairs of real and imaginary parts.

Try it online!

### How?

rp/ - Link: [R1, I1]; [R2, I2]
r   - inclusive range -> [[R1..R2], [I1..I2]]
/ - reduce by:
p  -   Cartesian product


rŒp does the same thing, where Œp is the Cartesian product of the items of [[R1..R2], [I1..I2]].

# Bash, 49 bytes

eval echo \{${1%,*}..${2%,*}},\{${1#*,}..${2#*,}}


Try it online!

# Desmos, 44 bytes

f(A,B)=[(X,Y)forX=[A.x...B.x],Y=[A.y...B.y]]


Complex numbers $$\a+bi\$$ are represented with coordinate pairs $$\(a,b)\$$. Input is two coordinate pairs, output is a list of coordinate pairs.

Try It On Desmos!

Try It On Desmos! - Prettified

# R, 30 bytes

\(a,b,c,d)expand.grid(a:c,b:d)


Attempt This Online!

Takes input as four numbers a,b,c,d and returns a matrix with real and imaginary parts in columns.

# R, 35 bytes

\(x,y)outer(x:y,Im(x):Im(y)*1i,+)


Attempt This Online!

Input and output as complex numbers.

# Ruby, 58 bytes

->a,b{r,i=a.zip b;[*r.min..r.max].product [*i.min..i.max]}


Attempt This Online!

# sclin, 29 bytes

";"zip Q*
,""sort"1+"' ,_ a>b


Try it here! Inputs/outputs pairs representing complex numbers.

For testing purposes:

[1 1_ ] [1_ 3] ; >A
";"zip Q*
,""sort"1+"' ,_ a>b


## Explanation

Prettified code:

\; zip Q*
, () sort 1.+ ' ,_ a>b

• \; zip zip inputs...
• , () sort pair and sort ascending
• 1.+ ' increment second number in pair
• ,_ a>b exclusive range from pair
• Q* Cartesian product

An inclusive range function would actually provide a substantial byte-save here, entirely removing the need to sort/increment pairs.

# Excel, 155 bytes

=LET(
a,+A1:A2,
b,HSTACK(SORT(IMREAL(a)),SORT(IMAGINARY(a))),
c,LAMBDA(d,LET(e,INDEX(b,1,d),+SEQUENCE(1+INDEX(b,2,d)-e,,e))),
TOCOL(COMPLEX(c(1),TOROW(c(2))))
)


Inputs are complex numbers in cells A1 and A2.

# Charcoal, 27 bytes

Ｆθ⊞υ⊟ιＩΣＥ…·⌊υ⌈υＥ…·⌊⌊θ⌈⌈θ⟦λι


Attempt This Online! Link is to verbose version of code. Uses pairs of integers for I/O, and takes a pair of pairs as input. Explanation:

Ｆθ⊞υ⊟ι


Separate out the imaginary parts.

ＩΣＥ…·⌊υ⌈υＥ…·⌊⌊θ⌈⌈θ⟦λι


Form inclusive ranges over the imaginary and real parts and make into pairs.

Previous 19-byte answer only worked with ascending ranges:

ＩΣＥ…·⊟θ⊟ηＥ…·ΣθΣη⟦λι


Attempt This Online! Link is to verbose version of code. Uses pairs of integers for I/O. Explanation:

   …·               Inclusive range from
⊟θ             First imaginary part to
⊟η           Second imaginary part
Ｅ                 Map over values
…·        Inclusive range from
Σθ      First real part to
Ση    Second real part
Ｅ          Map over values
λ  Real part
ι Imaginary part
⟦   Make into pair
Σ                  Flatten 1 level
Ｉ                   Cast to string
Implicitly print


# MATL, 5 bytes

:i:Z*


Input: two cell arrays of two numbers each. Output: pairs of numbers separated by newlines.

Try it online!

### Explanation

:    % Implicit input: cell array of two numbers. Range
i:   % Input: cell array of two numbers. Range
Z*   % Cartesian product. Implicit display


# 05AB1E, 5 bytes

ø€Ÿâ


Input as a pair of pairs of regular integers.

Explanation:

ø      # Zip/transpose the (implicit) input 2x2-block, swapping rows/columns
€     # Map over both pairs:
Ÿ    #  Convert the pair to a ranged list
# Pop and push both lists separately to the stack
â  # Pop both, and create all possible pairs with the cartesian product
# (after which the result is output implicitly)


# Japt, 7 bytes

I/O as pairs of integers

ÕËrõÃrï


Try it

ÕËrõÃrï     :Implicit input of 2D integer array
Õ           :Transpose
Ë          :Map
r         :  Reduce by
õ        :    Inclusive range
Ã       :End map
r      :Reduce by
ï     :  Cartesian product


# Haskell + hgl, 9 bytes

sQ<<zW eR


Takes two lists of length two as input.

>>> (sQ<<zW eR) [1,2] [-3,3]
[[1,2],[1,3],[0,2],[0,3],[-1,2],[-1,3],[-2,2],[-2,3],[-3,2],[-3,3]]


## Explanation

• zW eR zip with the reversable range
• sQ generalized cartesian product

## Reflection

• There should be a builtin for cartesian product. l2(,) is way too long.
• At this point Uc should be promoted to U. Uc is frequently used and its not like there is anything else that is going to use the U character.
• There should be a couple of things in terms of arrows that could be implemented for this.
• You program does not output the right result for some test-cases (both for the standard-input format (re1,im1) (re2,im2) and the format you answer seems to be using: (re1,re2), (im1,im2)) Oct 5, 2023 at 7:57
• @bsoelch Looks like I mixed up the similar ef and eR functions, switching to eR fixes the issues (I thought I tested these so I was probably using eR before I put it into ato). Changing the input format actually saves a bunch of bytes. Oct 5, 2023 at 12:30

# Mathematica, 100 bytes

100 bytes, it can be golfed much more.

Try it online!

f[a_,b_]:=Flatten@Table[r~Complex~i,{r,Re@a~Min~Re@b,Re@a~Max~Re@b},{i,Im@a~Min~Im@b,Im@a~Max~Im@b}]


# JavaScript (V8), 89 bytes

f=(x,y,X,Y=y)=>y-Y?f(x,y,X)|f(x,y+(Y>y||-1),X,Y):x-X?f(x,y)|f(x+(X>x||-1),y,X):print(x,y)


Try it online!

Silly