Circles of text [closed]

Find a way to make circles of a given radius using characters in a console. Please specify the font name and size. Also, please provide at least one example of the output.

For example:

Input:

3


Output:

   ******
**      **
**        **
*          *
**        **
**      **
******


...Well, something better looking than that "hand drawn" "circle" with a radius of 3.

Bonus question: Ellipses. :)

• Interestingly enough, my radius-3 circle is exactly identical to yours without even trying :) Mar 10, 2011 at 6:40
• Mar 10, 2011 at 8:26
• Maybe the font-part can be clarified. Copied here, all fonts will be the same; the same for font-size. Jun 7, 2012 at 13:12

a Bresenham circle in Scala (35)

The Bresenham - algorithm has 2 major points:

• works without sin/ cosin.
• you only calculate ¼*½ circle, the other points are found by mirroring.

How to do it:

       2 1
DCBABCD
GFE  |  EFG
IJ   y|----JI
GJ     |    /JG
F      |   / |F
DE      | r/  |ED
C       | /   | C
B 4     |/    | B 3
A       +-------A
B 4'          x B 3'
C               C
DE             ED
F             F
GJ           JG
IJ         JI
GFE     EFG
DCBABCD
2'1'

• We only calculate the numbers from A in the zenit to I.
• Point I is at 45°, defined by x == y.
• Ground zero is where the + is.
• The A in the zenit is the point (x=0, y=r), r = radius.
• To draw a closed circle we move clockwise (++x), which is to the right (x+=1) or down to the next point, (y-=1).
• every point(x,y) on the circle is r away from the center. Pythagoras says, r²=x²+y².
• This smells like square-root and equitations with 2 solutions, but beware!
• we start at A and want to know, whether we paint next the point below or the point beneath to the right.
• we calculate for both points (x²+y²) and build for both the difference to r² (which stays of course constant).
• since the difference can be negative, we take the abs from it.
• then we look which point is closer to the result (r²), eo ipso smaller.
• depending on that we draw the right or bottom neighbor.
• the so found point
• 1 x, y gets mirrored
• 2 -x, y to the left
• 3 y, x at the diagonal
• 4 -y, x from there to the left
• all those points get mirrored again to the south
• 1' x, -y
• 2' -x, -y
• 3' y, -x
• 4' -y, -x done.

This isn't code golf, but all those numbers at the top of the existing solutions made me think it is, so I spent useless time in golfing my solution. Therefore I added a useless number at the top too. It's 11 times Pi rounded.

object BresenhamCircle extends App {
var count = 0
val r = args(0).toInt
// ratio > 1 means expansion in horizontal direction
val ratio = args(1).toInt
val field = ((0 to 2 * r).map (i=> (0 to 2 * r * ratio).map (j=> ' ').toArray)).toArray
def square (x: Int, y: Int): Int = x * x + y * y
def setPoint (x: Int, y: Int) {
field (x)(y*ratio) = "Bresenham"(count)
field (y)(x*ratio) = "Bresenham"(count)
}
def points (x: Int, y: Int)
{
setPoint (r + x, r + y)
setPoint (r - x, r + y)
setPoint (r + x, r - y)
setPoint (r - x, r - y)
}
def bresenwalk () {
var x = 0;
var y = r;
val rxr = r * r
points (x, y);
do
{
val (dx, dy) = { if (math.abs (rxr - square ((x+1), y)) < math.abs (rxr - square (x, (y-1))))
(1, 0)
else
(0, -1)
}
count = (count + 1) % "Bresenham".length
x += dx
y += dy
points (x, y)
}while ((x <= y))
}
bresenwalk ()
println (field.map (_.mkString ("")).mkString ("\n"))
}


The font-question is decided by sites webserver and your browser settings. Now, that I'm looking it is

'Droid Sans Mono',Consolas,Menlo,Monaco,Lucida Console,Liberation Mono,DejaVu Sans Mono,Bitstream Vera Sans Mono,Courier New,monospace,serif


Font-size is 12px. Pretty useless information, if you ask me, but who does?

Bonus: ellipses and sample output:

The invocation is

    scala BresenhamCircle SIZE RATIO


for example

    scala BresenhamCircle 10 2
s e r B r e s
h n e           e n h
e m a                   a m e
e r                           r e
m                               m
h a                               a h
n                                   n
s e                                   e s
e                                       e
r                                       r
B                                       B
r                                       r
e                                       e
s e                                   e s
n                                   n
h a                               a h
m                               m
e r                           r e
e m a                   a m e
h n e           e n h
s e r B r e s

A ratio of 2 will print a circular shape for most fonts which happen to be about twice as tall than wide. To compensate for that, we widen by 2.
# As smaller value than 2 only 1 is available:

scala BresenhamCircle 6 1
erBre
aes   sea
ah       ha
e         e
es         se
r           r
B           B
r           r
es         se
e         e
ah       ha
aes   sea
erBre

# widening it has more freedom:

scala BresenhamCircle 12 5
s    e    r    B    r    e    s
a    h    n    e                             e    n    h    a
B    m                                                           m    B
e    r                                                                     r    e
e    s                                                                               s    e
B    r                                                                                         r    B
a    m                                                                                                   m    a
h                                                                                                             h
n                                                                                                             n
s    e                                                                                                             e    s
e                                                                                                                       e
r                                                                                                                       r
B                                                                                                                       B
r                                                                                                                       r
e                                                                                                                       e
s    e                                                                                                             e    s
n                                                                                                             n
h                                                                                                             h
a    m                                                                                                   m    a
B    r                                                                                         r    B
e    s                                                                               s    e
e    r                                                                     r    e
B    m                                                           m    B
a    h    n    e                             e    n    h    a
s    e    r    B    r    e    s


I restricted the ratio parameter for Int to keep it simple, but it can easily be widened to allow floats.

• your character count (without unneeded newlines) is in fact 34.557519189487725623089077216075 :) BTW: very nice solution, +1 Jun 7, 2012 at 12:59

Javascript (360)

function c(r){var f=1.83;var e=2*Math.PI/(r*r*r*r*r);var s=r*2+1;var g=Array(s);for(var i=0;i<s;i++){g[i]=Array(Math.round(s*f))};for(var i=0;i<=2*Math.PI;i+=e) {var x=Math.round(f*r*Math.cos(i)+f*r);var y=Math.round(r*Math.sin(i))+r;g[y][x]=1;}for(var j=0;j<g.length;j++){for(var i=0;i<g[j].length;i++)document.write((g[j][i]==1)?'*':' ');document.writeln()}}


http://jsfiddle.net/YssSb/3/ (f is a correction factor for the line-height / font-width ratio. If you use a square font setting, i.e., set line-height = font-size, you can set f=1 and get "square" circles. Or set f arbitrarily for ellipses.)

Output for 3 (interestingly enough, accidentally exactly the same shape as OP), 5, 15:

   ******
**      **
**        **
*          *
**        **
**      **
******

*********
***       ****
***            **
**               **
*                 *
*                 *
*                 *
**               **
***            **
***       ****
*********

***************
******             ******
****                       *****
***                              ***
***                                  ***
***                                      ***
**                                          **
**                                            **
**                                              **
**                                                **
**                                                  **
*                                                    *
**                                                    **
*                                                      *
*                                                      *
*                                                      *
*                                                      *
*                                                      *
**                                                    **
*                                                    *
**                                                  **
**                                                **
**                                              **
**                                            **
**                                          **
***                                      ***
***                                  ***
***                              ***
****                       *****
******             ******
***************

• Nice looking circles you've got. ;) Mar 15, 2011 at 0:21

Python (172)

172 chars including the two mandatory newlines. Uses the Bresenham algorithm for conic curves (no divisions or multiplications); it only outputs circles for square fonts, but should be exempt from staircase effects (ie. always has the same width).

y=input();t=[y*[' ']for x in range(y)];x=0;y-=1;p=3-2*y
while x<=y:t[x][y]=t[y][x]='*';n,y=((x-y+1,y-1),(x,y))[p<0];p+=4*n+6;x+=1
for s in t[::-1]+t:print"".join(s[::-1]+s)


Not very pretty, but well, I thought I'd give it a shot.

  ****
*    *
*      *
*      *
*      *
*      *
*    *
****

********
***        ***
*              *
*                *
*                  *
*                    *
*                      *
*                        *
*                        *
*                        *
*                          *
*                          *
*                          *
*                          *
*                          *
*                          *
*                          *
*                          *
*                        *
*                        *
*                        *
*                      *
*                    *
*                  *
*                *
*              *
***        ***
********


Edit: typo, replaced addition with division.

Perl (92)

I went for the “bonus question” and made it exploit the character aspect ratio to draw ellipses :)

($w)=@ARGV;for$x(-$w..$w){$p.=abs($x*$x+$_*$_-$w*$w)<$w?'*':$"for(-$w..$w);$p.=$/;}print$p;


Example outputs:

>perl circle.pl 3
***
*   *
*     *
*     *
*     *
*   *
***

>perl circle.pl 5
*****
*     *
*       *
*         *
*         *
*         *
*         *
*         *
*       *
*     *
*****

>perl circle.pl 8
*****
**     **
*         *
*           *
*             *
*             *
*               *
*               *
*               *
*               *
*               *
*             *
*             *
*           *
*         *
**     **
*****

• +1 3rd place, but the shapes don't look as nice as in the other answers. (Still better than what I could program, of course. :) ) Mar 15, 2011 at 0:24

g n=map(zipWith(?)f.repeat)f where x?y|abs(x^2+y^2-n^2)<n='*'|0<1=' ';f=[-n..n]
main=interact$unlines.g.read  This works by checking, whether x² + y² - r² < n for all points. All points for which this is true are stars, all others are blanks. Examples: $ echo 3 | runhaskell circ.hs
***
*   *
*     *
*     *
*     *
*   *
***
\$ echo 10 | runhaskell circ.hs
*******
**       **
*           *
*             *
*               *
*                 *
*                 *
*                   *
*                   *
*                   *
*                   *
*                   *
*                   *
*                   *
*                 *
*                 *
*               *
*             *
*           *
**       **
*******


See here for big example: http://www.ideone.com/t042u

Python, 180 characters

This code makes circles if the font is square. It's pretty easy to modify to generate nominal ellipses if you know your font height/width ratio.

import math
r=input()
d=2*r+1
c=[' '*d]*d
for a in xrange(9*d):f=math.pi*a/r/9; x=int(r+r*math.sin(f)+.5);y=int(r+r*math.cos(f)+.5);c[y]=c[y][:x]+'*'+c[y][x+1:]
for s in c:print s


Examples:

4:
*****
**   **
**     **
*       *
*       *
*       *
**     **
**   **
*****

7:
*****
**     **
**       **
**         **
**           **
*             *
*             *
*             *
*             *
*             *
**           **
**         **
**       **
**     **
*****

• Could you post a sample? Mar 12, 2011 at 0:53
• +1 But 2nd place... It was close, though. Mar 15, 2011 at 0:23

C, 127 Bytes, Font name: Arial Super Bold

#include<math.h>
main(){int r=10,c=r*2+1,q=c*c,d;for(;q--;)d=hypot(r-q%c,r-q/c),printf("%c%s",d>r-4&&d<=r?42:32,q%c?"":"\n");}


Result:

      *********
*************
***************
*****************
******       ******
*****         *****
*****           *****
****             ****
****             ****
****             ****
****             ****
****             ****
****             ****
****             ****
*****           *****
*****         *****
******       ******
*****************
***************
*************
*********

• 110 bytes Oct 10, 2021 at 19:55