我想使用 Tikz-pgf 或其他方式在圆内绘制相等的圆,如下图所示(请忘记小圆圈内的数字):
要绘制一个圆圈,我们可以使用:
\begin{tikzpicture}
\draw[color=red] (0,0) circle [radius=1];
\end{tikzpicture}
但是如何在这个单位圆内创建一个等圆,如第一张图所示?
一种方法是找到每个小圆的中心及其半径。但这非常技术性。
有没有什么绘图工具可以轻松做到这一点?例如,Wolfram 中有绘图工具,但需要订阅。
评论:先来看一下上面第一幅图,这是一个称为 p 进制的数字系统,该图显示了 3 进制数的分布。这是数学中一个有趣的数字系统。
答案1
干得好!
\documentclass[tikz,border=3.14mm]{standalone}
\begin{document}
\newcommand{\RA}{2}
\pgfmathsetmacro{\RB}{\RA*(1+2/sqrt(3)}
\begin{tikzpicture}
\draw (0,0) circle[radius=\RB cm];
\foreach \ang in {90,210,330}
\draw (\ang:\RB-\RA) circle[radius=\RA cm];
\end{tikzpicture}
\end{document}
当然,如果您想先画出外圆,然后根据外圆定义内圆,您可以稍微改变一下代码:
\documentclass[tikz,border=3.14mm]{standalone}
\begin{document}
\newcommand{\RA}{2}
\pgfmathsetmacro{\RB}{\RA/(1+2/sqrt(3)}
\begin{tikzpicture}
\draw (0,0) circle[radius=\RA cm];
\foreach \ang in {90,210,330}
\draw (\ang:\RA-\RB) circle[radius=\RB cm];
\end{tikzpicture}
\end{document}
奖励:第二次迭代
\documentclass[tikz,border=3.14mm]{standalone}
\usetikzlibrary{calc}
\begin{document}
\newcommand{\RA}{2}
\pgfmathsetmacro{\RB}{\RA/(1+2/sqrt(3)}
\begin{tikzpicture}
\draw (0,0) circle[radius=\RA cm];
\foreach \ang [count = \i from 1] in {90,210,330}
\draw (\ang:\RA-\RB) coordinate (center-\i) circle[radius=\RB cm];
\pgfmathsetmacro{\RC}{\RB/(1+2/sqrt(3)}
\foreach \i in {1,2,3}
\foreach \ang in {90,210,330}
\draw ($(center-\i)+(\ang:\RB-\RC)$) circle[radius=\RC cm];
\end{tikzpicture}
\end{document}
如果您只需要两次迭代,那么它就做得非常粗略。如果您需要更多迭代,则需要使代码更清晰、更实用。
答案2
数学问题通过以下方法解决:SebGlav 已在评论中他们的回答也给你带来了很大的帮助。
我想提供一个使用循环节点和标签(即更多节点)的递归解决方案。
它使用ext.pgfkeys-plus
我的tikz-ext
包裹/utils/TeX/ifnum={<test>}{<true>}{<false>}
当达到零级时,结束递归的键。(如果您不能使用它,它的定义在下面的代码中。)
其背后的想法是将标签(即另一个圆内的圆)锚定在角度 90、210 和 330 处以及它们的父节点处。这样,我们只需要计算半径,PGF/TikZ 就会计算出它的三角函数。
第二幅图将递归检查移到内部,cic/label
这样我们就可以使用级别 0 来做一些完全不同的事情。此外,还引入了另一个参数(#3
其中cic/@
replacedcic
现在只是一个“启动器”),该参数被传递下去并显示#2
为cic/node'
。
它仅包含一个列表方向u
以(90°)、l
(210°)和r
(330°)的形式。
因为这只是一个三元数,我们也可以用级别#1
和数字进行一些计算来代替它0
,1
并2
动态地评估这些值,但在这里我选择对这些进行硬编码。
代码
\documentclass[tikz]{standalone}
%\usepgfkeyslibrary{ext.pgfkeys-plus}
\makeatletter
\pgfkeys{/utils/TeX/ifnum/.code n args={3}{%
\ifnum#1\relax\expandafter\pgfutil@firstoftwo\else\expandafter\pgfutil@secondoftwo\fi
{\pgfkeysalso{#2}}{\pgfkeysalso{#3}}}}
\makeatother
\begin{document}
\tikz[
cic/node/.style={
shape=circle, inner sep=+0pt, outer sep=+0pt, minimum size={#1}},
cic/.style n args={2}{
cic/node={#2}, cic/level #1/.try,
/utils/TeX/ifnum={#1=0}{}{
/utils/exec=%
\pgfmathsetlengthmacro\rad{#2/(1+2/sqrt(3))}%
\pgfmathtruncatemacro\level{#1-1},
cic/label/.expanded={\level}{\rad}{ 90},
cic/label/.expanded={\level}{\rad}{210},
cic/label/.expanded={\level}{\rad}{330}}},
cic/label/.style n args={3}{
label={[anchor=#3, label position=#3, cic={#1}{#2}]}},
cic/level setter/.style args={#1=#2}{cic/level #1/.style={fill=#2}},
cic/level setter/.list={3=purple, 2=red!50, 1=green!50!black, 0=blue!50},
] \node[cic={3}{2cm}]{};
\tikz[
cic/node/.style={
shape=circle, inner sep=+0pt, outer sep=+0pt, minimum size={#1}},
cic/node'/.style 2 args={% this node contents is just a debug fall back
cic/node={#1}, path only, node contents={#2}, cic/node #2/.try},
cic/.style 2 args={cic/@={#1}{#2}{cic-}},
cic/@/.style n args={3}{
cic/node={#2}, cic/level #1/.try,
/utils/exec=\pgfmathsetlengthmacro\rad{#2/(1+2/sqrt(3))},
cic/label/.expanded={\inteval{#1-1}}{\rad}{ 90}{#3u},
cic/label/.expanded={\inteval{#1-1}}{\rad}{210}{#3l},
cic/label/.expanded={\inteval{#1-1}}{\rad}{330}{#3r}},
cic/label/.style n args={4}{
/utils/TeX/ifnum={#1=0}{
label={[anchor=#3, label position=#3, cic/node'={#2}{#4}]},
}{
label={[anchor=#3, label position=#3, cic/@={#1}{#2}{#4}]}}},
cic/level setter/.style args={#1=#2}{cic/level #1/.style={fill=#2}},
cic/level setter/.list={2=purple, 1=red!50},
cic/node setter/.style args={#1=#2}{
cic/node cic-#1/.style={node contents={#2}}},
cic/node setter/.list={uu=0, ru=1, lu=2, ur=3, rr=4, lr=5, ul=6, rl=7, ll=8}
] \footnotesize\node[cic={2}{2cm}]{};
\end{document}