Das Problem, das ich modelliere: Auf einem Kreis werden drei zufällig ausgewählte Punkte ausgewählt. Wie groß ist die Wahrscheinlichkeit, dass das von diesen drei Punkten gebildete Dreieck den Mittelpunkt des Kreises enthält?
Konzeptionelles Verständnis: Angenommen, wir fixieren zwei der drei Punkte und nennen sie A und B. Damit das Dreieck den Mittelpunkt enthält, muss der dritte Punkt C innerhalb des Bogens A'B' liegen, wobei A' und B' das Bild der Punkte A bzw. B bei einer Drehung um 180 Grad sind.
Was ich will, dass passiert: Das zufällig generierte einbeschriebene Dreieck wird grün ausgefüllt, wenn es den Mittelpunkt enthält, und rot, wenn es den Mittelpunkt nicht enthält. Ich möchte auch die Anzahl der Erfolge und Misserfolge zählen, um eine experimentelle Wahrscheinlichkeit zu berechnen.
Ein paar wichtige Dinge: Ich habe Zugriff auf die x- und y-Koordinaten jedes Punkts, indem ich \pgfextractx
und verwende \pgfextracty
. Meine Methode bestand darin, zu testen, ob der Punkt C zwischen den x- und y-Koordinaten von A und B liegt \xintifboolexpr
, indem ich verwendet habe. Dies ist jedoch fehlerhaft.
Minimales Arbeitsbeispiel:
\documentclass{article}
\usepackage[left=2cm, right=2cm, top=2cm, bottom=1cm]{geometry}
\usepackage{amsmath,amsfonts,tikz,xintexpr,calc}
\newcommand\circletest{
\begin{tikzpicture}[scale=0.6]
\newdimen{\tempxa}
\newdimen{\tempya}
\newdimen{\tempxb}
\newdimen{\tempyb}
\newdimen{\tempxc}
\newdimen{\tempyc}
\def\radius{2}
\draw (0,0) coordinate (O);
\draw (O) circle[radius=\radius];
\draw (rnd*360:\radius) coordinate (A);
\pgfextractx\tempxa{\pgfpointanchor{A}{center}}
\pgfextracty\tempya{\pgfpointanchor{A}{center}}
\draw (rnd*360:\radius) coordinate (B);
\pgfextractx\tempxb{\pgfpointanchor{B}{center}}
\pgfextracty\tempyb{\pgfpointanchor{B}{center}}
\draw (rnd*360:\radius) coordinate (C);
\pgfextractx\tempxc{\pgfpointanchor{C}{center}}
\pgfextracty\tempyc{\pgfpointanchor{C}{center}}
\xintifboolexpr { (((\tempxc > -\tempxa) && (\tempxc < -\tempxb)) || ((\tempxc > -\tempxb) && (\tempxc < -\tempxa))) && (((\tempyc > -\tempya) && (\tempyc < -\tempyb)) || ((\tempyc > -\tempyb) && (\tempyc < -\tempya)))} %%I know this is grotesque
{\filldraw[color=green!80!black!100, fill=green!15] (A) -- (B) -- (C) -- cycle;} %true
{\filldraw[color=red!80!black!100, fill=red!15] (A) -- (B) -- (C) -- cycle;} %false
\fill[black] (A) circle[radius=2pt];
\fill[black] (B) circle[radius=2pt];
\fill[black] (C) circle[radius=2pt];
\fill[black] (O) circle[radius=2pt];
\draw (A) node[below]{A};
\draw (B) node[below]{B};
\draw (C) node[below]{C};
\end{tikzpicture}}
\begin{document}
\foreach \x in {0,1,...,11}{
\circletest
}
\end{document}
Das Problem, das ich habe: Offensichtlich ist mein Vergleichsoperator \xintifboolexpr
zusammen mit meinem darauf folgenden grotesken Code das Problem. Ich suche nach einer einfacheren Methode, um festzustellen, ob der Punkt C auf dem Kreisbogen zwischen (-\tempax,-\tempay)
und liegt (-\tempbx,-\tempby)
.
BEARBEITEN: Eine korrekte Lösung aus dem Vorschlag von Sandy G.
\documentclass{article}
\usepackage[left=2cm, right=2cm, top=2cm, bottom=1cm]{geometry}
\usepackage{amsmath,amsfonts,tikz,xintexpr,calc}
\usepackage{xfp}
\newcommand\circletest{
\begin{tikzpicture}[scale=0.6]
\pgfmathsetmacro{\rndA}{rnd*360}
\pgfmathsetmacro{\rndB}{rnd*360}
\pgfmathsetmacro{\rndC}{rnd*360}
%defining x and y coordinates of each point
\def\radius{2}
\def\xa{\fpeval{\radius*cosd(\rndA)}}
\def\ya{\fpeval{\radius*sind(\rndA)}}
\def\xb{\fpeval{\radius*cosd(\rndB)}}
\def\yb{\fpeval{\radius*sind(\rndB)}}
\def\xc{\fpeval{\radius*cosd(\rndC)}}
\def\yc{\fpeval{\radius*sind(\rndC)}}
%calculating side lengths of triangle
\def\A{\fpeval{sqrt((\xb-\xc)^2 + (\yb-\yc)^2)}}
\def\B{\fpeval{sqrt((\xa-\xc)^2 + (\ya-\yc)^2)}}
\def\C{\fpeval{sqrt((\xa-\xb)^2 + (\ya-\yb)^2)}}
%calculating angles of triangle
\def\angleA{\fpeval{acosd((\B^2 + \C^2 -\A^2)/(2*\B*\C))}}
\def\angleB{\fpeval{acosd((\C^2 + \A^2 -\B^2)/(2*\C*\A))}}
\def\angleC{\fpeval{acosd((\A^2 + \B^2 -\C^2)/(2*\A*\B))}}
%defining some coordinates
\draw (0,0) coordinate (O);
\draw (O) circle[radius=\radius];
\draw (\xa,\ya) coordinate (A);
\draw (\xb,\yb) coordinate (B);
\draw (\xc,\yc) coordinate (C);
%test if center is in circle
\xintifboolexpr{((\angleA < 90) && (\angleB < 90)) && (\angleC < 90)}
{\filldraw[color=green!80!black!100, fill=green!15] (A) -- (B) -- (C) -- cycle;} %true
{\filldraw[color=red!80!black!100, fill=red!15] (A) -- (B) -- (C) -- cycle;} %false
%Drawing points on top of line
\draw[fill=black] (\xa,\ya) circle(1.5pt);
\draw[fill=black] (\xb,\yb) circle(1.5pt);
\draw[fill=black] (\xc,\yc) circle(1.5pt);
\draw[fill=black] (O) circle(1.5pt);
\end{tikzpicture}}
\begin{document}
\foreach \x in {0,1,...,30}{
\circletest
}
\end{document}
Antwort1
Man kann die calc
Bibliothek nutzen unddieses Rezept, das Ihrem sehr ähnlich ist, aber vielleicht etwas kürzer. Durch die Verwendung der calc
Bibliothek können wir auch die Einführung neuer Dimensionen vermeiden. Die Definition von a pic
hat den Vorteil, dass Sie Ti verwenden könnenkZ, um die Zeichnungen beliebig anzuordnen.
\documentclass{article}
\usepackage[left=2cm, right=2cm, top=2cm, bottom=1cm]{geometry}
\usepackage{tikz}
\usetikzlibrary{calc}
\begin{document}
What is the probability for the triangle containing the origin? Without loss of
generality we can take the angle of $A$ to be 0 (because one can rotate the
setup without changing the probability). Then the angle of $B$, $\beta$ can be
chosen to be between $0$ and $\pi$ (because one can reflect the setup at the
$x$--axis without changing the probability). Then the angle of $C$,
$\gamma$, needs to satisfy
\[ \pi<\gamma<\pi+\beta \]
for the center to be inside the triangle, see Figure~\ref{fig:derivation}.
As $\beta$ scans the domain $[0,\pi]$, the probability for a triangle with
corners at random positions of the circle enclosing the center of the circle is
$1/4$.
\begin{figure}[ht]
\centering
\begin{tikzpicture}[dot/.style={circle,inner sep=1pt,fill},
declare function={rr=2.5;}]
\begin{scope}
\draw (0,0) circle[radius=rr] (0,0) -- (rr,0) node[dot,label=right:$A$]{};
\pgfmathsetmacro{\rndB}{rnd*90}
\draw (1,0) arc[start angle=0,end angle=\rndB,radius=1]
node[midway,anchor=180+\rndB/2,circle]{$\beta$}
(0,0) -- (\rndB:rr) node[dot,label={[anchor=\rndB+180]:$B$}]{};
\draw[dashed] (180+\rndB:rr) -- (0,0) -- (180:rr);
\draw[blue,thick] (180:rr) arc[start angle=180,end angle=180+\rndB,radius=rr]
node[midway,anchor=\rndB/2,circle,align=right]{allowed\\ positions\\ for $C$};
\end{scope}
%
\begin{scope}[xshift=2.8*rr*1cm]
\draw (0,0) circle[radius=rr] (0,0) -- (rr,0) node[dot,label=right:$A$]{};
\pgfmathsetmacro{\rndB}{90+rnd*90}
\draw (1,0) arc[start angle=0,end angle=\rndB,radius=1]
node[midway,anchor=180+\rndB/2,circle]{$\beta$}
(0,0) -- (\rndB:rr) node[dot,label={[anchor=\rndB+180]:$B$}]{};
\draw[dashed] (180+\rndB:rr) -- (0,0) -- (180:rr);
\draw[blue,thick] (180:rr) arc[start angle=180,end angle=180+\rndB,radius=rr]
node[midway,anchor=\rndB/2,circle,align=right]{allowed\\ positions\\ for $C$};
\end{scope}
\end{tikzpicture}
\label{fig:derivation}
\end{figure}
\begin{figure}[ht]
\centering
\begin{tikzpicture}[pics/circletest/.style={code={
\tikzset{circletest/.cd,#1}%
\def\pv##1{\pgfkeysvalueof{/tikz/circletest/##1}}%
\draw (0,0) coordinate (O) circle[radius=\pv{r}];
\pgfmathsetmacro{\rndA}{rnd*360}
\pgfmathsetmacro{\rndB}{rnd*360}
\pgfmathsetmacro{\rndC}{rnd*360}
\path (\rndA:\pv{r}) coordinate[label={[anchor=\rndA+180]:$A$}] (A)
(\rndB:\pv{r}) coordinate[label={[anchor=\rndB+180]:$B$}] (B)
(\rndC:\pv{r}) coordinate[label={[anchor=\rndC+180]:$C$}] (C);
\draw let \p1=(A),\p2=(B),\p3=(C),\p0=(O),
\n1={(\x0-\x2)*(\y1-\y2)-(\x1-\x2)*(\y0-\y2)},
\n2={(\x0-\x3)*(\y2-\y3)-(\x2-\x3)*(\y0-\y3)},
\n3={(\x0-\x1)*(\y3-\y1)-(\x3-\x1)*(\y0-\y1)}
in \pgfextra{\pgfmathtruncatemacro\itest{%
((\n1 < 0) || (\n2 < 0) || (\n3 < 0)) &&
((\n1 > 0) || (\n2 > 0) || (\n3 > 0))}}
\ifnum\itest=0
[color=green!80!black!100, fill=green!15] (A) -- (B) -- (C) -- cycle
\else
[color=red!80!black!100, fill=red!15] (A) -- (B) -- (C) -- cycle
\fi;
\fill (O) circle[radius=1pt] node[below]{$O$};
}},circletest/.cd,r/.initial=1]
\path foreach \X in {1,...,5}
{ foreach \Y in {1,...,5} {(3*\X,3*\Y) pic{circletest}}};
\end{tikzpicture}
\end{figure}
\end{document}
Ein alternativer Vorschlag, der auf Schnittpunkten basiert. Konstruieren Sie einen Strahl, der den Kreis von seinem Mittelpunkt aus verlässt. Wenn die Anzahl der Schnittpunkte mit dem Dreieck gerade ist, liegt der Mittelpunkt außerhalb des Dreiecks, andernfalls innerhalb.
\documentclass{article}
\usepackage[left=2cm, right=2cm, top=2cm, bottom=1cm]{geometry}
\usepackage{tikz}
\usetikzlibrary{intersections}
\begin{document}
\begin{tikzpicture}[pics/circletest/.style={code={
\tikzset{circletest/.cd,#1}%
\def\pv##1{\pgfkeysvalueof{/tikz/circletest/##1}}%
\draw (0,0) coordinate (O) circle[radius=\pv{r}];
\pgfmathsetmacro{\rndA}{rnd*360}
\pgfmathsetmacro{\rndB}{rnd*360}
\pgfmathsetmacro{\rndC}{rnd*360}
\path (\rndA:\pv{r}) coordinate[label={[anchor=\rndA+180]:$A$}] (A)
(\rndB:\pv{r}) coordinate[label={[anchor=\rndB+180]:$B$}] (B)
(\rndC:\pv{r}) coordinate[label={[anchor=\rndC+180]:$C$}] (C);
\path[name path=triangle] (A) -- (B) -- (C) -- cycle;
\path[name path=ray,overlay] (O) -- ({180+(\rndA+\rndB+\rndC)/3}:1.5*\pv{r});
\draw[name intersections={of=triangle and ray,total=\t}]
\ifodd\t
[color=green!80!black!100, fill=green!15] (A) -- (B) -- (C) -- cycle
\else
[color=red!80!black!100, fill=red!15] (A) -- (B) -- (C) -- cycle
\fi;
}},circletest/.cd,r/.initial=1]
\path foreach \X in {1,...,5}
{ foreach \Y in {1,...,5} {(3*\X,3*\Y) pic{circletest}}};
\end{tikzpicture}
\end{document}
Dieser Ansatz ist durch die Genauigkeit der Schnittpunkte begrenzt und kann fehlschlagen, wenn das Dreieck zu dünn ist, also im Wesentlichen eine Linie darstellt.
PS: Diese Verteilungen stimmen mit der tatsächlichen Wahrscheinlichkeit überein.
Antwort2
Um meine Neugier bezüglich der experimentellen Wahrscheinlichkeit zu befriedigen, habe ich dies in getan metapost
. Es scheint etwa 100.000 Dreiecke zu erfordern, um die theoretische Wahrscheinlichkeit (d. h. 1/4) auf 3 Dezimalstellen genau zu erhalten. Wenn Sie die Zeichenbefehle kommentieren, um nur das Ergebnis auszudrucken, dann dauern 1.000.000 Durchläufe nur wenige Sekunden. Ein Teil der Ausgabe für 20.000 eingeschriebene Dreiecke in 1-mm-Kreisen:
\documentclass{article}
\usepackage{luamplib}
\usepackage{geometry}
\mplibnumbersystem{double}
\mplibtextextlabel{enable}
\mplibcodeinherit{enable}
\begin{document}
\begin{mplibcode}
vardef triarray(expr r,n)=
save x,tmp,width;
width:=\mpdim{\linewidth} div r;
count:=0;
tot:=n;
for j=0 upto n:
% for the grid
drawoptions(withpen pencircle scaled .1bp shifted ((r+.1)*(j mod width),-(r+.1)*(j div width)));
for i=1 upto 3: x[i]:=uniformdeviate(8); endfor;
% sort vals, probably didn't need to, but made things tidier.
if x1>x2:
tmp:=x1; x1:=x2; x2:=tmp;
fi;
if x2>x3:
tmp:=x2; x2:=x3; x3:=tmp;
if x1>x2:
tmp:=x1; x1:=x2; x2:=tmp;
fi;
fi;
% end sort
% points on a circle in mp are mapped to the interval [0,8] with 0->0 and 8->360
% reflected points rather than rotating arc
if ((x1+4) mod 8>x2) and ((x1+4) mod 8<x3) and ((x3+4) mod 8>x1) and ((x3+4) mod 8<x2):
fill fullcircle scaled r withcolor .2[white,green];
count:=count+1;
else:
fill fullcircle scaled r withcolor .2[white,red];
fi;
% uncomment below for the triangles
draw for i=1 upto 3: point x[i] of (fullcircle scaled r)-- endfor cycle;
endfor;
enddef;
beginfig(0);
triarray(1mm,20000);
endfig;
\end{mplibcode}
\begin{mplibcode}
beginfig(1);
picture p; string s;
s="$\frac{"&decimal(count)&"}{"&decimal(tot)&"}="&decimal(count/tot)&"$";
p= s infont defaultfont scaled defaultscale;
draw p;
endfig;
\end{mplibcode}
\end{document}