简体   繁体   English

在2D数组中创建圆的算法编辑:钻石会很好

[英]algorithm to create a circle in a 2D array EDIT: diamond would be okay aswel

I have a 2D in python that represents a tile map, each element in the array is either a 1 or 0, 0 representing land and 1 representing water. 我在python中有一个2D代表一个瓦片地图,数组中的每个元素都是1或0,0代表土地,1代表水。 I need an algorithm that takes 2 random coordinates to be the center of the circle, a variable for the radius (max 5) and replace the necessary elements in the array to form a full circle. 我需要一种算法,该算法将2个随机坐标作为圆的中心,将半径作为变量(最大值为5),并替换数组中的必要元素以形成一个完整的圆。

x = random.randint(0,MAPWIDTH)
y = random.randint(0,MAPHEIGHT)
rad = random.randint(0,5)

tileMap[x][y] = 1 #this creates the center of the circle

how would I do this? 我该怎么做?

You would have to set a coordinate to one if ((x – h)(x - h)) + ((y – k)(y - k)) = r * r is true. 如果((x – h)(x - h)) + ((y – k)(y - k)) = r * r为真,则必须将坐标设置为1。 h is the centre x coordinate and k is the centre y coordinate. h是中心x坐标, k是中心y坐标。

As previously said, you can use the definition of a circle, like so: 如前所述,您可以使用圆的定义,如下所示:

import math

def dist(x1, y1, x2, y2):
    return math.sqrt((x1 - x2) ** 2 + (y1 - y2) ** 2)

def make_circle(tiles, cx, cy, r):
    for x in range(cx - r, cx + r):
        for y in range(cy - r, cy + r):
            if dist(cx, cy, x, y) <= r:
                tiles[x][y] = 1

width = 50
height = 50

cx = width // 2
cy = height // 2
r = 23

tiles = [[0 for _ in range(height)] for _ in range(width)]

make_circle(tiles, cx, cy, r)

print("\n".join("".join(map(str, i)) for i in tiles))

This outputs 这个输出

00000000000000000000000000000000000000000000000000
00000000000000000000000000000000000000000000000000
00000000000000000000000001000000000000000000000000
00000000000000000001111111111111000000000000000000
00000000000000001111111111111111111000000000000000
00000000000000111111111111111111111110000000000000
00000000000001111111111111111111111111000000000000
00000000000111111111111111111111111111110000000000
00000000001111111111111111111111111111111000000000
00000000011111111111111111111111111111111100000000
00000000111111111111111111111111111111111110000000
00000001111111111111111111111111111111111111000000
00000001111111111111111111111111111111111111000000
00000011111111111111111111111111111111111111100000
00000111111111111111111111111111111111111111110000
00000111111111111111111111111111111111111111110000
00001111111111111111111111111111111111111111111000
00001111111111111111111111111111111111111111111000
00001111111111111111111111111111111111111111111000
00011111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00111111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00011111111111111111111111111111111111111111111100
00001111111111111111111111111111111111111111111000
00001111111111111111111111111111111111111111111000
00001111111111111111111111111111111111111111111000
00000111111111111111111111111111111111111111110000
00000111111111111111111111111111111111111111110000
00000011111111111111111111111111111111111111100000
00000001111111111111111111111111111111111111000000
00000001111111111111111111111111111111111111000000
00000000111111111111111111111111111111111110000000
00000000011111111111111111111111111111111100000000
00000000001111111111111111111111111111111000000000
00000000000111111111111111111111111111110000000000
00000000000001111111111111111111111111000000000000
00000000000000111111111111111111111110000000000000
00000000000000001111111111111111111000000000000000
00000000000000000001111111111111000000000000000000
00000000000000000000000000000000000000000000000000
00000000000000000000000000000000000000000000000000

Note that I deliberately used a rather large array and radius - this results in being able to actually see the circle a bit better. 请注意,我故意使用了相当大的数组和半径-这样可以实际看到更好的圆。 For some radius around 5, it would probably be pixelated beyond belief. 对于大约5的某个半径,它可能会难以置信地被像素化。

Inspired by Izaak van Dongen, just re-worked a bit: 受到Izaak van Dongen的启发,做了一些修改:

from pylab import imshow, show, get_cmap
from numpy import random
import math

def dist(x1, y1, x2, y2):
    return math.sqrt((x1 - x2) ** 2 + (y1 - y2) ** 2)

def make_circle(tiles, cx, cy, r):
    for x in range(cx - r, cx + r):
        for y in range(cy - r, cy + r):
            if dist(cx, cy, x, y) < r:
                tiles[x][y] = 1
    return tiles

def generate_image_mask(iw,ih,cx,cy,cr):

    mask = [[0 for _ in range(ih)] for _ in range(iw)]
    mask = make_circle(mask, cx, cy, cr)
    #print("\n".join("".join(map(str, i)) for i in mask))
    imshow(mask, cmap=get_cmap("Spectral"), interpolation='nearest')
    show()

if __name__ == '__main__':

    image_w = 60
    image_h = 60
    circle_x = image_w/2
    circle_y = image_h/2
    circle_r = 15

    generate_image_mask(image_w,image_h,circle_x,circle_y,circle_r)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM