-1

I'm writing a code to create a diagram of crater density. Essentially, every new crater is plotted as a circle, and circles are allowed to overlay each other (because new craters can erase old ones). I was wondering if there's any way to remove circles that have been overlain, or to create a counter to only count how many uninterrupted circles there are? My objective is to count how many 'fresh' craters (circles) there are that haven't been erased by other ones. The first code is my code for creating and plotting these circles (the xx+1, yy+1 is to add a 'shadow' effect).

fig, ax = pl.subplots()

#this is going to create a random list to pull center coordinates from
xcenter = np.random.randint(501, size = 500)
ycenter = np.random.randint(501, size = 500)
#start a counter at 0 so we can see the progression of time
time = 0
#now to zip the x and y center coordinates and make circles
for xx, yy in zip(xcenter, ycenter): 
    cratershadow = Circle((xx, yy),5, color = 'b')
    ax.add_patch(cratershadow)
    crater = Circle((xx+1, yy+1), 5, color = 'c')
    ax.add_patch(crater)
    time += 1
#setting the axiis(?) to be up to 500 km
ax.set_xlim((0,500))
ax.set_ylim((0,500))
pl.xlabel("X side, 500 km Field")
pl.ylabel("Y side, 500 km Field")
pl.title("Crater Density Plot - 500,000 years")
pl.show()
Laura
  • 1
  • it would help to include your `import` statements, I figured them out and made the plot. But the problem is beyond this forum's scope - you need to decide an approach Object Oriented or not is just the 1st choice – f5r5e5d Nov 17 '17 at 03:28

1 Answers1

0

You need to remember all the craters in some form of list and on any new added one check for intersections/overlaps. If any crater is fully inside remove it from the list. Plot only the final result of the list.

You can also do a time-line structure where each crater would have start and end time so instead of removal from list just set its end time from infinity to the time the new crater was added. This way you can animate the density over time.

Sorry I am not a python coder but in a C++ it would look something like this:

struct _crater
 {
 int x,y,r; // center and radius
 int t0,t1; // start and end time
 };

List<_crater> crater;

To check if 2 craters i,j intersect/overlap you can test their distance...

int d=sqrt(((crater[i].x-crater[j].x)*(crater[i].x-crater[j].x))+((crater[i].y-crater[j].y)*(crater[i].y-crater[j].y)));
if (d>=crater[i].r+crater[j].r); // too far away or just touching
if (d< crater[i].r+crater[j].r); // intersect or overlap
if (crater[i].r>=crater[j].r)
 if (d<=crater[i].r-crater[j].r); // i fully covers j

In case you implemented the time line you need to take into account only craters that are current... and ignore the other ones.

To speed this up you can use sorting and binary search ...

Spektre
  • 49,595
  • 11
  • 110
  • 380