20
\$\begingroup\$

Given two integers as input in an array, draw a rectangle, using the first integer as width and second as height.

Or, if your language supports it, the two integers can be given as separate inputs.

Assume the width and height will never be less than 3, and they will always be given.

Example Outputs:

[3, 3]

|-|
| |
|-|

[5, 8]

|---|
|   |
|   |
|   |
|   |
|   |
|   |
|---|

[10, 3]

|--------|
|        |
|--------|

This is code-golf, so the answer with the lowest amount of bytes wins.

\$\endgroup\$

41 Answers 41

1
\$\begingroup\$

C#, 102 93 bytes

Saved 9 bytes thanks to milk - completely forgot to concatenate strings. The compare trick is pretty cool too.

w=>h=>{var s="";for(int i=0;i<h;)s+="|"+new String(1>i++%(h-1)?'-':' ',w-2)+"|\n";return s;};

Try it online!

Full source, including test cases:

using System;

namespace DrawASCIIRectangle
{
    class Program
    {
        static void Main(string[] args)
        {
            Func<int,Func<int,string>> d= w=>h=>{var s="";for(int i=0;i<h;)s+="|"+new String(1>i++%(h-1)?'-':' ',w-2)+"|\n";return s;};
            Console.WriteLine(d(3)(3));
            Console.WriteLine(d(5)(8));
            Console.WriteLine(d(10)(3));
        }
    }
}
\$\endgroup\$
  • 1
    \$\begingroup\$ Using 1>i++%(h-1) instead of i++<1||i>h-1 will save 1 byte. You can also put all the string concats into a single statement so the for is a one liner and doesn't need braces, saving another 8 bytes: s+="|"+new string(1>i++%(h-1)?'-':' ',w-2)+"|\n" \$\endgroup\$ – milk Sep 19 '16 at 19:44
1
\$\begingroup\$

bash, sed and coreutils, 95 89 bytes

You can define a function like this

f(){ n=$[$1-2];yes \ |sed $[$2*n]q|tr -d \\n|fold -w$n|sed 's/^\|$/|/g;1!{$!b};s/ /-/g';}

Or in a more readable format:

f() { 
  n=$(($1-2))

  # The next couple of lines create a rectangle of spaces
  # matching the desired size
  yes ' '          |
  head -n$(($2*n)) |
  tr -d '\n'       |
  fold -w$n        |

  # Add the pipes and dashes
  sed '
    s/^\|$/|/g   # Replace first and last character by a pipe
    1! {$!b }    # Do nothing if not on first or last line
    s/ /-/g      # Add the dashes
  '
  echo
}

You can now say f 4 3:

|--|
|  |
|--|

If you care about trailing new-line, add an echo at the end of function.

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

Python (70 bytes)

def r(w,h): print '\n'.join(['|'+('-' if i%(h-1)==0 else ' ')*(w-2)+'|' for i in range(h)])

Edit: lambda function for a few less bytes (thanks @DJMcMayhem)

r=lambda w,h:'\n'.join(['|'+('-'if i%(h-1)==0 else' ')*(w-2)+'|'for i in range(h)])

Edit#2: if notation is greedy

r=lambda w,h:'\n'.join(['|'+(0<i<h-1 and' 'or'-')*(w-2)+'|'for i in range(h)])

Edit#3: -8 bytes with list trick

r=lambda w,h:'\n'.join(['|'+'- '[0<i<h-1]*(w-2)+'|'for i in range(h)])
\$\endgroup\$
  • \$\begingroup\$ Hello, welcome to the site! Some tips, 1) you have some unnecessary whitespace that you could remove. 2) A lambda function is shorter since you don't need to call print (you can just return instead) \$\endgroup\$ – DJMcMayhem Sep 19 '16 at 5:19
  • \$\begingroup\$ I count 83 bytes \$\endgroup\$ – TuxCrafting Sep 19 '16 at 8:54
1
\$\begingroup\$

C 87 bytes

f(b,a,c,k){for(;c<a*b;++c)printf("%s",(k=c%b)==b-1?"|":!k?"\n|":c<b||c>a*b-b?"-":" ");}

this is the main for some test...

main() 
{f(3,3,0,0); f(5,8,0,0); f(10,3,0,0);
 return 0;
}


|-|
| |
|-|
|---|
|   |
|   |
|   |
|   |
|   |
|   |
|---|
|--------|
|        |
|--------|
\$\endgroup\$
0
\$\begingroup\$

Pyth, 22 bytes

VJE.[Q*-Q2?}N,0tJ\-d\|

A program that takes input of the width, followed by the height, on STDIN and prints the result.

Try it online

How it works

VJE.[Q*-Q2?}N,0tJ\-d\|  Program. Inputs: Q, E
 JE                     Assign E to J
V                       For N in [0, 1, 2, ..., J-1]:
             ,0tJ        Yield [0, J-1]
           }N            N is in that list
          ?              If that:
                 \-       Yield "-"
                         Else:
                   d      Yield " "
      *-Q2               Repeat that Q-2 times
   .[Q              \|   Evenly pad that with "|" on both sides to length Q
                         Implicitly print
\$\endgroup\$
0
\$\begingroup\$

Actually, 35 bytes

¬'|@α(¬;)' *╗`╜o'|o`Mi('-*"|%s|"%;)

Try it online!

Explanation:

¬'|@α(¬;)' *╗`╜o'|o`Mi('-*"|%s|"%;)
¬                                    height - 2
 '|@α                                ["|" for _ in range(height-2)]
     (¬;)                            width - 2, duplicate, move to bottom of stack
         ' *                         " "*(width-2)
            ╗                        save to register 0
             `╜o'|o`M                for each "|" in list of "|"s:
              ╜o                       append (width-2) spaces
                '|o                    append a second "|"
                     i               flatten list
                      (              bring copy of (width-2) back to top
                       '-*           "-"*(width-2)
                          "|%s|"%    surround with "|"s
                                 ;)  dupe, move copy to bottom of stack
                                     (implicitly print stack contents, one element per line)
\$\endgroup\$
0
\$\begingroup\$

Racket 108 bytes

(λ(w h)(for((j h))(display #\|)(for((i(- w 2)))(display(if(or(= j 0)(= j(- h 1)))#\-" ")))(displayln #\|)))

Ungolfed:

(define f
  (λ (w h)
    (for ((j h)) 
      (display #\|)
      (for ((i (- w 2)))
        (display (if (or
                      (= j 0)
                      (= j (- h 1)))
                     #\-
                     " ")))
      (displayln #\|))))

Testing:

(f 5 3)

Output:

|---|
|   |
|---|
\$\endgroup\$
0
\$\begingroup\$

APL (Dyalog Unicode), 25 bytes

'|','|',⍨'-'⍪'-'⍪⍨''⍴⍨-∘2

Try it online!

-∘2 subtract two

''⍴⍨ use that as height and width to reshape an empty string (padding with spaces)

'-'⍪⍨ put dashes below

'-'⍪ put dashes on top

'|',⍨ put stiles on the right

'|', put stiles on the left

\$\endgroup\$
0
\$\begingroup\$

Python, 105 bytes

[a,b]=input().split()
def d(e):print("|"+e*(int(a)-2)+"|")
d("-")
for f in range(2,int(b)):d(" ")
d("-")

Try it online

\$\endgroup\$
0
\$\begingroup\$

tcl, 99

puts [set M |[string repe - [incr w -2]]|]
incr w
time {puts |[format %$w\s |]} [incr h -2]
puts $M

demo

\$\endgroup\$
0
\$\begingroup\$

Python 3, 68 bytes

def f(a,b):
 c='|'+'-'*(a-2)+'|\n';print(c+c.replace(*'- ')*(b-2)+c)
\$\endgroup\$

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.