我正在尝试为我的阻塞分析论文创建甘特图。我知道pgfgantt
用于生成甘特图的软件包。但是这个软件包会生成常规时间表的图表,我需要的是专门用于阻塞分析的甘特图,就像操作系统教科书中使用的那些一样。
下面是我需要的一个例子:
如何使用 pdflatex 制作类似这样的图表?我也不介意使用 pgfgantt,只是我不知道它如何呈现这样的内容。
答案1
我抗拒不了:
\documentclass{standalone}
\usepackage{tikz}
\usetikzlibrary{calc,arrows.meta,decorations.pathreplacing}
\newcounter{gridw}
\newcounter{procs}
\newif\ifinpgroup
\inpgroupfalse
\newenvironment{schedulechart}[1]{%
\begin{tikzpicture}[x=10,y=15,>=latex,
processbox/.style={draw,fill=white},
pendingbox/.style={fill=black!25},
midstroke/.style={path picture={\draw (path picture bounding box.west) -- (path picture bounding box.east);}},
divided/.style={path picture={\draw (path picture bounding box.north west) -- (path picture bounding box.south east);}}]
\setcounter{gridw}{#1}
\setcounter{procs}{0}
\def\gridw{\thegridw}
\foreach\x in {0,...,\gridw}{
\draw[black!25] ({\x+1},0) -- ++(0,1);
\pgfmathparse{Mod(\x,5)==0?1:0};
\ifnum\pgfmathresult>0
\draw ({\x+1},0) coordinate (c\x) -- ({\x+1},.5);
\node at ([yshift=-5]c\x.south) {\x};
\else
\draw ({\x+1},0) coordinate (c\x) -- ({\x+1},.25);
\fi
}
}{%
\draw[<->,>={Latex[open]}] (0,{\procs+1}) -- (0,0) -- ({\gridw+2},0);%
\end{tikzpicture}
}
\newcommand{\process}[3][]{
\stepcounter{procs}
\def\procs{\theprocs}
\draw[black!25] (0,\procs) coordinate (r\procs) -- ({\gridw+1},\procs);
\foreach\x in {0,...,\gridw}
\draw[black!25] ({\x+1},\procs) -- ++(0,1);
\ifinpgroup\else
\if\relax\detokenize{#1}\relax\else
\node[anchor=east] at ([yshift=5,xshift=-25]r\procs.west) {$#1$:};
\fi
\draw[black!25] (r\procs.west) -- ++(-5,0);
\fi
\node[anchor=east] at ([yshift=5,xshift=0]r\procs.west) {$#2$};
\begin{scope}[yshift={\procs*15}]
#3
\end{scope};
}
\newcommand{\processstart}[2][]{
\foreach\x/\y in {#2}
\draw[processbox,#1] ({\x+1},0) coordinate (a) rectangle ({\y+1},.5);
\draw[->] (a) -- ++(0,.9);
}
\newcommand{\processmid}[2][]{
\foreach\x/\y in {#2}
\draw[pendingbox,#1] ({\x+1},.1) rectangle ({\y+1},.4);
}
\newcommand{\processblock}[2][]{
\foreach\x/\y in {#2}
\draw[processbox,divided] ({\x+1},0) rectangle ({\y+1},.5)
node[anchor=north east,inner sep=1pt,xshift=1pt] {\tiny $#1$};
}
\newcommand{\processend}[2][]{
\foreach\x/\y in {#2}
\draw[processbox,#1] ({\x+1},0) rectangle ({\y+1},.5) coordinate (a);
\draw[-|] (a) -- ++(0,.25);
}
\newenvironment{processgroup}[1]{
\inpgrouptrue
\def\procs{\theprocs}
\draw[black!25] ([yshift=15]r\procs.west) coordinate (g0) -- ++(-5,0);
\def\processgroupname{#1}
}{
\path (g0) -- coordinate[midway] (m) (r\procs.west);
\draw[decorate,decoration={brace}] ([xshift=-22]g0) -- ([xshift=-22,yshift=10]r\procs.west);
\node[anchor=east] at ([yshift=5,xshift=-25]m) {$\processgroupname$:};
\inpgroupfalse
}
\begin{document}
\begin{schedulechart}{15}
\process[P_1]{J_1}{\processstart{1/3}\processmid[fill=none,midstroke]{3/10}\processend{10/12}}
\process[P_2]{J_2}{\processstart{0/2}\processmid[fill=none,midstroke]{2/7}\processend{7/9}}
\process[P_3]{J_3}{\processstart{0/1}\processmid[fill=none,midstroke]{1/4}\processend{4/7}}
\begin{processgroup}{P_4}
\process{J_4}{\processstart{0/1}\processmid{1/10}\processend{10/13}}
\process{A_1}{\processstart{2/2}\processmid{2/4}\processblock[J_2]{4/7}\processblock[J_1]{7/10}}
\process{A_2}{\processstart{1/1}\processblock[J_3]{1/4}}
\end{processgroup}
\end{schedulechart}
\end{document}
产量: