我需要绘制 $ X - (Y \cap Z) 的维恩图,但我只能弄清楚如何得到 $X - (Y \cup) Z)?有人能帮忙吗?
\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{shapes,backgrounds}
\begin{document}
\def\firstcircle{(0,0) circle (1.5cm)}
\def\secondcircle{(60:2cm) circle (1.5cm)}
\def\thirdcircle{(0:2cm) circle (1.5cm)}
\begin{tikzpicture}
\begin{scope}[shift={(6cm,0cm)}]
\begin{scope}[even odd rule]% first circle without the second
\clip \thirdcircle (-3, -3) rectangle (3,3);
\clip \secondcircle (-3, -3) rectangle (3,3);
\fill[yellow] \firstcircle;
\end{scope}
\draw \firstcircle node {$X$};
\draw \secondcircle node {$Y$};
\draw \thirdcircle node {$Z$};
\end{scope}
\end{tikzpicture}
答案1
这里有一个不同的方法。我们用白色填充第二和第三个圆圈,然后用黄色填充第一个圆圈。最后,我们将三个圆圈的交叉点涂成白色。
\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{shapes,backgrounds}
\begin{document}
\def\firstcircle{(0,0) circle (1.5 cm)}
\def\secondcircle{(0: 2 cm) circle (1.5 cm)}
\def\thirdcircle{(60:2 cm) circle (1.5 cm)}
\begin{tikzpicture}
%Define the circles for the Venn diagram for three sets.
\draw[fill=white] \secondcircle;
\draw[fill=white] \thirdcircle;
\draw[fill=yellow] \firstcircle;
% Label the sets.
\node[left] at (0, 0) {\(X\)};
\node[above] at (60: 2 cm) {\(Y\)};
\node[right] at (0: 2 cm) {\(Z\)};
%Color the intersection of all three circles white.
\begin{scope}
\clip \firstcircle;
\clip \secondcircle;
\draw[fill=white] \thirdcircle;
\end{scope}
%Draw the circles.
\draw \firstcircle;
\draw \secondcircle;
\draw \thirdcircle;
\end{tikzpicture}
生成图表
答案2
只是为了好玩!
\documentclass[border=10pt,pstricks]{standalone}
\begin{document}
\begin{pspicture}(-3,-4)(6,6)
\psclip[linestyle=none]{%
\pscircle[fillstyle=solid,fillcolor=pink](0,0){3}}
\psclip{%
\pscircle[fillstyle=solid,fillcolor=pink](3;60){3}}
\pscircle[fillstyle=solid,fillcolor=white](3,0){3}
\endpsclip
\endpsclip
\pscircle(0,0){3} \rput(-1.5,-0.5){$X \setminus (Y \cap Z)$}
\pscircle(3,0){3} \rput(1.5,3.5){$Y$}
\pscircle(3;60){3} \rput(3.5,-0.5){$Z$}
\end{pspicture}
\end{document}
答案3
有一个专门用于维恩图的包:venndiagram
。需要对它进行一些“破解”,因为您要找的交点似乎不在预定义的集合中,但这就是它的用途\setpostvennhook
。这个破解定义了圆的内部和轮廓。它们的名称为 A、B 和 C,但它们的标签可以设置为 X、Y 和 Z。
\documentclass[border=10pt]{standalone}
\usepackage{venndiagram}
\makeatletter% https://tex.stackexchange.com/a/499947
\tikzset{interior/.style={insert path={
(\csname @venn@#1x\endcsname,\csname @venn@#1y\endcsname) circle[radius=\@venn@radius-\pgflinewidth/2]}},
contour/.style={insert path={
(\csname @venn@#1x\endcsname,\csname @venn@#1y\endcsname) circle[radius=\@venn@radius]}}}
\makeatother
\begin{document}
\begin{venndiagram3sets}[labelA=$X$,labelB=$Y$,labelC=$Z$]
\fillA
\setpostvennhook{
\clip[interior=B];
\fill[white,interior=C];
\draw[contour=A];}
\end{venndiagram3sets}
\end{document}
附录:由于这是一个重复的主题,我尝试在这里收集一些标准技巧,并在venndiagram
曲目中添加一些内容。
- 这
reverse clip
诡计可以夹在任何东西上外部给定的路径。 - 这
even odd clip
诡计允许将其应用于even odd rule
剪辑。 - 我添加了样式
interior of
,它生成一条包含 A、B 或 C 内部的路径,contour of
允许重新绘制 A、B 或 C 的轮廓,以及common of
,允许检索两个集合的交集。后者需要库calc
。
使用这些技巧,可以避免白色过度涂抹。我们首先剪掉 B 和 C 交点之外的所有东西,
\clip[common of=B and C,reverse clip];
然后填充 A 的内部,
\fill[\VennShade,interior of=A];
完成 MWE。(请注意,要小心不要添加任何硬编码距离,这样做的目的是为了生成多个图表并具有通用设置。)
\documentclass[border=10pt]{standalone}
\usepackage{venndiagram}
\usetikzlibrary{calc,backgrounds}
\makeatletter% https://tex.stackexchange.com/a/499947
\tikzset{interior of/.style={insert path={
(\csname @venn@#1x\endcsname,\csname @venn@#1y\endcsname) circle[radius=\@venn@radius-\pgflinewidth/2]}},
contour of/.style={insert path={
(\csname @venn@#1x\endcsname,\csname @venn@#1y\endcsname)
circle[radius=\@venn@radius]}},
midpoint of/.style={insert path={
(\csname @venn@#1x\endcsname,\csname @venn@#1y\endcsname)
}},
common of/.style args={#1 and #2}{insert path={
let \p1=($(\csname @venn@#2x\endcsname,\csname @venn@#2y\endcsname)-(\csname @venn@#1x\endcsname,\csname @venn@#1y\endcsname)$),
\n1={veclen(\y1,\x1)/2},\n2={sqrt(\@venn@radius*\@venn@radius-\n1*\n1)},
\n3={atan2(\y1,\x1)},\n4={atan2(\n2,\n1)} in
($(\csname @venn@#1x\endcsname,\csname @venn@#1y\endcsname)+(\n3+\n4:\@venn@radius)$)
arc(\n3+\n4:\n3-\n4:\@venn@radius) arc(\n3+180+\n4:\n3+180-\n4:\@venn@radius)
-- cycle
%\pgfextra{\typeout{\n2,\n3,\n4,\@venn@radius}}
}},
reverse clip/.style={insert path={{% https://tex.stackexchange.com/a/127045
[overlay] (0,0) -|
(\@venn@w,\@venn@h) -| cycle
}}},
even odd clip/.code={% https://tex.stackexchange.com/a/76216
\pgfseteorule}}
\def\VennShade{\@venn@shade}
\makeatother
\begin{document}
\begin{venndiagram3sets}[labelA=$X$,labelB=$Y$,labelC=$Z$]
\setpostvennhook{
\begin{scope}[on background layer]
\clip[common of=B and C,reverse clip];
\fill[\VennShade,interior of=A];
\end{scope}}
\end{venndiagram3sets}
\end{document}
答案4
就像 Taussig 上面所做的那样,这是clip
TikZ 的常见做法。考虑到 TikZ 代码的简洁性和灵活性,我可能有点难以理解。
\documentclass[tikz,border=5mm]{standalone}
\begin{document}
\begin{tikzpicture}
\def\r{1.5} \def\d{1}
\def\firstC{(90:\d) circle(\r)}
\def\secondC{(-30:\d) circle(\r)}
\def\thirdC{(210:\d) circle(\r)}
\fill[magenta!30] \firstC;
\begin{scope}
\clip \firstC;
\clip \secondC;
\fill[white] \thirdC;
\end{scope}
\draw \firstC \secondC \thirdC;
\path
(90:1.2*\d) node[magenta,scale=.6]{$A\setminus (B\cap C)$}
(90:2*\d) node{$A$}
(210:2*\d) node{$B$}
(-30:2*\d) node{$C$};
\end{tikzpicture}
\end{document}
这是 Asymptote 代码的翻译(完全相同的图片)。
unitsize(1cm);
real r=1.5,d=1;
pair A=d*dir(90),B=d*dir(210),C=d*dir(-30);
path firstC=circle(A,r);
path secondC=circle(B,r);
path thirdC=circle(C,r);
fill(firstC,.3magenta+.7white);
picture BcapC;
fill(BcapC,thirdC,white);
clip(BcapC,firstC);
clip(BcapC,secondC);
add(BcapC);
draw(firstC^^secondC^^thirdC);
label("$A$",2A);
label("$B$",2B);
label("$C$",2C);
label((scale(.6))*"$A\setminus (B\cap C)$",1.2A,magenta);
add(bbox(5mm),Fill(white));