Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    text
    copied!<p>This might get you started. It is a simple rejection method to generate circles at random, throwing away ensembles that do not meet requirements.</p> <p>Arguments are the box size, numbers and radii of small and large circles, and a minimum separation. That last is used both for distances to boundary and distances between circles. I double it for the center of gravity to center of frame constraint. Clearly this usage could be generalized by adding more arguments.</p> <p>For purposes of assessing how likely this is to find viable ensembles, I print the number of times through the loop. Also I use a Catch/Throw mechanism that is not really necessary (artifact of some experimentation that I did not bother to remove).</p> <p>--- edit ---</p> <p>The code below has modest changes from what I originally posted. It separates the center of gravity circle as the red one.</p> <p>To handle the constraint that it lie at some specified angle, one might generate as below, rotate to put into the correct angular position, and recheck distances from circles to frame boundary. Possibly there is something smarter that will be less likely to give a rejection, while still maintaining uniformity. Actually I'm not at all certain that what I coded gives a uniform distribution from the space of allowable configurations. If it does, the influence of rotating will very likely destroy that property.</p> <p>--- end edit ---</p> <pre><code>randomConfiguration[{xlo_, ylo_}, {xhi_, yhi_}, nsmall_, nlarge_, rsmall_, rlarge_, minsep_] := Catch[Module[ {found = False, xsmall, ysmall, xlarge, ylarge, smallsep, largesep, smallcircs, largecircs, cog, cen, indx = 0}, smallsep = {rsmall + minsep, -rsmall - minsep}; largesep = {rlarge + minsep, -rlarge - minsep}; cen = {xhi - xlo, yhi - ylo}; While[! found, found = True; indx++; xsmall = RandomReal[{xlo, xhi} + smallsep, nsmall]; ysmall = RandomReal[{ylo, yhi} + smallsep, nsmall]; xlarge = RandomReal[{xlo, xhi} + largesep, nlarge]; ylarge = RandomReal[{ylo, yhi} + largesep, nlarge]; smallcircs = Transpose[{xsmall, ysmall}]; Do[If[ Norm[smallcircs[[i]] - smallcircs[[j]]] &lt;= 2*rsmall + minsep, found = False; Break[]], {i, nsmall - 1}, {j, i + 1, nsmall}]; largecircs = Transpose[{xlarge, ylarge}]; Do[If[ Norm[largecircs[[i]] - largecircs[[j]]] &lt;= 2*rlarge + minsep, found = False; Break[]], {i, nlarge - 1}, {j, i + 1, nlarge}]; Do[If[ Norm[smallcircs[[i]] - largecircs[[j]]] &lt;= rsmall + rlarge + minsep, found = False; Break[]], {i, nsmall}, {j, nlarge}]; cog = (rsmall^2*Total[smallcircs] + rlarge^2*Total[largecircs])/(nsmall*rsmall^2 + nlarge*rlarge^2); If[Norm[cog - cen] &lt;= 2*minsep, found = False;]; ]; Print[indx]; Throw[{{cog, rsmall},Map[{#, rsmall} &amp;, smallcircs], Map[{#, rlarge} &amp;, largecircs]}] ]] </code></pre> <p>Example:</p> <pre><code>{smallc, largec} = randomConfiguration[{4.32, 3.23}, {35.68, 26.75}, 5, 3, 1, 2, 1]; 13 FraXYs = {{4.32, 3.23}, {35.68, 26.75}}; {cog, smallc, largec} = randomConfiguration[{4.32, 3.23}, {35.68, 26.75}, 5, 3, 1, 2, 1]; Graphics[{White, EdgeForm[Thick], Rectangle @@ FraXYs, Red, Apply[Disk, cog], Blue, Opacity[.6], EdgeForm[Black], Blue, Thickness[0.003], Opacity[1], Black, Disk[#[[1]], #[[2]]] &amp; /@ Join[smallc, largec]}, ImageSize -&gt; {400, 300}] </code></pre> <p><img src="https://i.stack.imgur.com/hhSQf.png" alt="enter image description here"></p>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload