在源文件中,我们可以看到各种版本,用于定义诸如限制等内容。所以我的问题是,哪个版本用于什么用途。在选择其中一个版本时,是否有任何“最佳实践”?
答案1
\operatorname
什么时候用(或其包装器\DeclareMathOperator
) 代替更好\mathop
?答案很简单:总是这样,除非你确切知道 的行为是什么\mathop
。
首先,当然必须记得\operatorname
和\DeclareMathOperator
是由amsopn
包提供的,该包由自动加载amsmath
,但也可以独立使用。
让我们看看主要的定义:
\DeclareRobustCommand{\operatorname}{%
\@ifstar{\qopname\newmcodes@ m}%
{\qopname\newmcodes@ o}}%
\DeclareRobustCommand{\qopname}[3]{%
\mathop{#1\kern\z@\operator@font#3}%
\csname n#2limits@\endcsname}
\newcommand{\DeclareMathOperator}{%
\@ifstar{\@declmathop m}{\@declmathop o}}
\long\def\@declmathop#1#2#3{%
\@ifdefinable{#2}{%
\DeclareRobustCommand{#2}{\qopname\newmcodes@#1{#3}}}}
该命令\qopname
实际上并非用于文档中;其第一个参数的目的是添加一些声明,例如\newmcodes@
在排版运算符名称之前。
\operatorname
和各自\DeclareMathOperator
都有一个 *-variant,它传递给\qopname
第二个参数m
而不是o
。后一个命令只是一个包装器:
\DeclareMathOperator{\xyz}{xyz}
\DeclareMathOperator*{\XYZ}{XYZ}
几乎相当于说
\DeclareRobustCommand{\xyz}{\operatorname{xyz}}
\DeclareRobustCommand{\XYZ}{\operatorname*{XYZ}}
(但处理得更有效)所以我们需要检查的只是\operatorname
。
调用\operatorname{xyz}
翻译为
\qopname\newmcodes@ o {xyz}
变成
\mathop{\newmcodes@\kern\z@\operator@font xyz}\csname nolimits@\endcsname}
声明
\newmcodes@
注意某些字符在数学公式中像平常一样被不同地处理(特别是连字符不会变成减号);\kern\z@
插入一个不可见的对象,这样整个内容\mathop
就永远不会是一个字符(参见https://tex.stackexchange.com/a/41267/4427了解详情);\operator@fonts
选择数学运算符的预定义字体,通常是直立的文本字体;\nolimits@
只是 的别名\nolimits
,因此除非声明取消,否则后面的下标和上标不会在运算符的上方和下方排版\limits
。
对于它来说\operatorname*
,它完全相同,唯一的区别是\nmlimits@
将执行 而不是\nolimits@
。此宏定义为等同于\displaylimits
,这使得运算符的行为类似于标准\lim
或\min
。
如果某个操作符在文档中只使用几次,那么可能无需用 定义命令\DeclareMathOperator
;但在我看来,如果使用适当的逻辑结构名称,源代码的可读性会增强。
需要\mathop
记住的是,它不会选择任何特定的字体,也不会纠正一些小故障:因此
\mathop{\mathrm{abc-def}}
将会有所不同
\operatorname{abc-def}
后者通常是预期的。在某些罕见情况下,\mathop
它本身就很有用:
\newcommand{\diff}{\mathop{}\!d}
是一个例子,其中空格\mathop
用于在“d”之前提供正确的间距。请注意,如果确实想要一个直立的“d”,将其定义为是不正确的,\operatorname{d}
并且与之前相同,应该使用\mathrm{d}
而不是d
:明确地,替代方案是
\newcommand{\diff}{\mathop{}\!\mathrm{d}}
此外\stackrel
,更好的amsmath
命令\overset
是\underset
用内部定义的\mathop{...}\limits
,但包裹在其他一些构造中。
答案2
\mathop
是最原始的命令,声明班级字符或子公式为一元数学运算符例如\sum
。与二元运算符用\mathbin
或声明二元关系\mathrel
例如用 声明。
大多数数学运算符都以文本名称写出。一些定义来自latex.ltx
:
\def\max{\mathop{\operator@font max}}
\def\min{\mathop{\operator@font min}}
\def\sup{\mathop{\operator@font sup}}
\def\inf{\mathop{\operator@font inf}}
\def\arg{\mathop{\operator@font arg}\nolimits}
\def\ker{\mathop{\operator@font ker}\nolimits}
\def\dim{\mathop{\operator@font dim}\nolimits}
\def\hom{\mathop{\operator@font hom}\nolimits}
您会看到使用了一种特殊的字体\operator@font
;此外,还可以看到,用声明的运算符\mathop
通常是排版的有限制,即在显示模式下,上标和下标被放置在特殊位置。可以使用 关闭此功能\nolimits
。
\operatorname
来自 AMSTeX 包将其封装为用户命令:
\DeclareRobustCommand{\operatorname}{%
\@ifstar{\qopname\newmcodes@ m}%
{\qopname\newmcodes@ o}}%
\DeclareRobustCommand{\qopname}[3]{%
\mathop{#1\kern\z@\operator@font#3}%
\csname n#2limits@\endcsname}
这基本上意味着\operatorname{dual}
将排版一个看起来像\arg
(即没有限制)的数学运算符“dual”并且将排版一个看起来像(即有限制)的\operatorname*{dual}
数学运算符“dual” 。\max
\DeclareMathOperator
是相应的声明,即\DeclareMathOperator\dual{dual}
创建一个新的宏\dual
,其工作原理类似于\max
。
关于使用:
- 使用
\mathop
,任何东西都可以声明为数学运算符,即如果您想使用*
前缀运算符(有限制),您只需说\mathop{*}
。 \DeclareMathOperator
如果您想定义一个新的运算符(如),则应该使用\max
。\operatorname
应用于仅需要一次特殊操作符名称的特殊情况。
答案3
\mathop
是一个纯 TeX 命令,它声明了一个大运算符,例如
\newcommand{\Res}{\mathop{\hbox{Res}}}
DeclareMathOperator
来自 AmsMath 的amsopn
子包,称为:
\DeclareMathOperator{\Res}{Res}
而是operatorname
一种“即时”操作符。输入
\operatorname{Res}
与或\Res
定义的含义相同mathop
DeclareMathOperator
我认为,如果您加载了 AmSMath(始终是个好主意),那么我会使用DeclareMathOperator
,并且operatorame
在文件中很少使用此运算符的情况下,或者使数学模式下的某些文本直立并使用空格填充。