LaTeX绘图备忘之编译原理相关例图绘制一
此文是为了方便以后绘制类似图形而写。本示例中使用了tikz宏包来绘制主体图形,使用qtree宏包绘制语法树。
示例图选自《编译原理》第2版第1章“图1-7 一个赋值语句的翻译”。下面是完整的示例代码:
% 博客园,繁星间漫步,陆巍的博客
\documentclass{article}
% 注意宏包顺序,有可能会报错
\usepackage{ctex}% 中文支持
\usepackage{geometry}% 用于页面设置
\usepackage{booktabs}% 增强表格功能
\usepackage{colortbl}% 表格颜色
\usepackage{multirow}% 支持表格的多行合并
\usepackage{longtable}% 支持长表格跨页
\usepackage{tikz}% 绘图
\usepackage{qtree}% 绘制语法分析树
% 载入tikz中的各种功能库
\usetikzlibrary{arrows.meta, chains, graphs}
% 设置为A4纸,边距适中模式(参考永中office)
\geometry{
a4paper,
left = 19.1mm,
right = 19.1mm,
top = 25.4mm,
bottom = 25.4mm
}
% 定义表格对齐方式
\newcolumntype{L}[1]{>{\raggedright\arraybackslash}p{#1}}
\newcolumntype{C}[1]{>{\centering\arraybackslash}p{#1}}
\newcolumntype{R}[1]{>{\raggedleft\arraybackslash}p{#1}}
% tikz图形样式定义
% rectangle
\tikzset{
rect1/.style = {
shape = rectangle,
draw = black,
thick,
align = center,
minimum height = 5ex,
}
}
% ------------------ 开始 -------------------
\begin{document}
\small
\begin{center}
\begin{tikzpicture}[
start chain = going below,
node distance = 2.5ex,
rect1,
every node/.style = {
text width = 14em,
minimum height = 3ex
},
>={Latex[length = 2mm, width = 1mm]},
]
\node[on chain](a){position = initial + rate * 60};
\node[draw, on chain](b){词法分析器};
\node[on chain, text width = 18em](c){
?id, 1? ?=? ?id, 2? ?+? ?id, 3? ?*? ?60?
};
\node[draw, on chain](d){语法分析器};
\node[on chain](e){
\Tree [.=
{?id, 1?} [.+
{?id, 2?} [.*
{?id, 3?} 60 ]
]
]
};
\node[draw, on chain](f){语义分析器};
\node[on chain, text width = 18em](g){
\Tree [.=
{?id, 1?} [.+
{?id, 2?} [.*
{?id, 3?} [.inttofloat 60 ]
]
]
]
};
\node[draw, on chain](h){中间代码生成器};
\node[on chain, align = left, text width = 10em](i){
t1 = inttofloat(60)\\
t2 = id3 * t1\\
t3 = id3 + t2\\
id1 = t3
};
\node[draw, on chain](j){代码优化器};
\node[on chain, align = left, text width = 10em](k){
t1 = id3 * 60.0\\
id1 = id2 + t1
};
\node[draw, on chain](l){代码生成器};
\node[on chain](m){
\begin{tabular}{p{3em}p{10em}}
LDF & R2, id3\\
MULF & R2, R2, \#60.0\\
LDF & R1, id2\\
ADDF & R1, R1, R2\\
STF & id1, R1
\end{tabular}
};
\node[left = 10em of f, text width = 9em]{
\begin{tabular}{p{1em}|p{4em}|C{2em}|}
\cline{2-3}
1 & position & ...\\
\cline{2-3}
2 & initial & ...\\
\cline{2-3}
3 & rate & ...\\
\cline{2-3}
& &\\
\cline{2-3}
\multicolumn{3}{c}{}\\
\multicolumn{3}{c}{符号表}
\end{tabular}
};
\graph [use existing nodes]{
a->b->c->d->e->f->g->h->i->j->k->l->m;
};
\end{tikzpicture}
\normalsize 图1-7\quad 一个赋值语句的翻译
\end{center}
\end{document}
生成效果如下:
注意事项:
1、注意其中使用的tikz中的三个库:arrows.meta、chains与graphs。其中使用graphs库后,可以在编写箭头时更为简洁。例如,在未使用graphs库之前,编写箭头时是使用\draw命令来逐个实现,使用graphs库后,就可以像示例代码中那样一连串的写出;
2、注意chains库的使用方法;
3、注意箭头形状的定义方法:
>={Latex[length = 2mm, width = 1mm]}
4、注意绘制语法树时经常会被遗忘的空格:
\Tree [.=
{?id, 1?} [.+
{?id, 2?} [.*
{?id, 3?} 60 ]
]
]
代码中60与]之间一定要有空格。
5、注意绘制左侧“符号表”时的表格相关命令:\cline、\multicolumn。灵活使用这些命令可以绘制复杂的表格。