TeXでの整数を扱う三つの方法
0.はじめに
TeX(特に e-TeX 拡張を前提とした場合)において「整数」を取り扱う方法のうち,character・number・counter という3種類の概念と,それら相互の変換を6パターン解説します。
-
character:
"1"
,"2"
,"12"
などの 数字を表す文字列- 今回は一桁だけ (
"1"
) のケースも二桁以上 ("12"
) のケースも共に考えます
- 今回は一桁だけ (
- counter: カウンタで管理される 整数。
-
number: TeX エンジン内部で扱われる 整数。
\numexpr ... \relax
などで数値計算できる対象。
counterもnumberも内部的には同じ整数ですが、前者は名前で管理されるのに対し、後者は制御綴で管理されます。
- number :
\hoge
などの制御綴に格納される。\newcount
がこれにあたる。 - counter : LaTeXでは
\newcounter
で定義される。
\newcount と \newcounterの違い
\newcount
- LaTeXの原型であるPlain TeXの命令。
- 汎用的な整数カウンターを作成します。
- シンプルに整数の値を保持するために使われ、段落番号や特定のカスタムカウントに便利です。
- リセット機能がありません。自分でリセットする必要があります。
\newcount\mycount % カウンターを新しく作成
\mycount=5 % 値を設定
\advance\mycount by 1 % 値を加算
\the\mycount % 現在の値を出力
\newcounter
- LaTeXの命令で、LaTeXドキュメント内のカウンター管理を簡単にするために作られています。
- 文書のセクション番号や、図表、項目リストなどの自動カウンターを管理するのに向いています。
- スコープごとのリセット機能があります。例えば、セクションごとに図表の番号をリセットすることが可能です。
\newcounter{mycounter} % カウンターを新しく作成
\setcounter{mycounter}{5} % 値を設定
\stepcounter{mycounter} % 値を1増加
\arabic{mycounter} % 現在の値をアラビア数字で出力
- 主な違い
機能 | \newcount |
\newcounter |
---|---|---|
対応環境 | Plain TeX, LaTeX | LaTeX専用 |
リセット機能 | なし | 章や節ごとのリセットが可能 |
使い方 | シンプルな整数管理 | 文書構造に基づく自動カウンター |
追加命令 | 手動加算、減算 |
\stepcounter や\addtocounter など |
1. TeX における整数の扱い
1.1 character(文字列)
文字列としての "12"
は TeX から見ると “1” と “2” の文字トークンの連なりです。
一桁の場合の "3"
などは、文字トークンが1つだけになるだけで基本的には同じ考え方です。
1.2 number(内部整数)
TeX では整数演算をする際に、\numexpr ... \relax
(e-TeX)や Plain TeX の \number
などを介して処理します。
-
\numexpr 12 \relax
→ “12” という整数値 -
\numexpr 12\relax
→ とすれば12
が取得できます。 - 一桁の場合でも
\numexpr 3 \relax
とすれば3
が取得できます。
1.3 counter
counterを使うと、整数を格納しておくことができます。
\newcounter{mycounter} % カウンターを新しく作成
\setcounter{mycounter}{5} % 値を設定
\stepcounter{mycounter} % 値を1増加
\arabic{mycounter} % 現在の値をアラビア数字で出力
2. 変換方法
ここからは以下の6種類の相互変換パターンを具体例とともに示します。
数字が一桁 ("3"
) でも二桁 ("12"
) でも同様の手順です。
- character → number
- number → character
- number → counter
- counter → number
- character → counter
- counter → character
前提として、「character」は "12"
や "3"
のような数字文字列、「number」は e-TeX の \numexpr
等で扱える内部整数とします。
2.1 character → number
目的
"12"
のような文字列(あるいは "3"
のような一桁文字列)を、TeX が演算できる整数(number)に変換したい
方法
- e-TeX の
\numexpr
は、文字列として渡された「数字」をそのまま整数として読んでくれます。 - 例えば以下のように書くと、
#1
が"12"
でも"3"
でも問題なく整数として読み取ります。
% #1 は "12" や "3" のような数字文字列を想定
\def\CharacterToNumber#1{%
\numexpr #1\relax
}
\CharacterToNumber{12} % -> 12
\CharacterToNumber{3} % -> 3
\relaxとは?
TeXの\relaxは、特定の動作を持たないプリミティブコマンドで、主にマクロの展開抑制や条件分岐の制御に使用されます。以下に具体的な例を挙げて説明します。
- マクロの展開抑制
\edef
内で特定のコマンドの展開を防ぐ際に\relax
を使用します。
\def\name{John}
\edef\greeting{Hello, \name\relax!}
この場合、\relax
がないと、\name
が展開されてしまいますが、\relax
を挿入することで、\name
の展開を抑制できます。
- 条件分岐の制御
\if
系の条件分岐で、予期しないトークンの読み込みを防ぐために\relax
を挿入します。
\ifmmode\relax
% 数式モードの場合の処理
\else
% 通常モードの場合の処理
\fi
このように、\ifmmode
の直後に\relax
を置くことで、条件判定が意図した通りに行われるようになります。
- 単位の後に挿入して曖昧さを回避
\hskip
や\vskip
で長さを指定する際、\relax
を用いて曖昧さを避けます。
\hskip 2.5pt\relax
\relax
を挿入することで、\hskip
が後続のplus
やminus
を誤って解釈するのを防ぎます。 
- 式の終了の明示
以下の例では、\numexpr
によって5 + 3
の計算が行われ、結果は8
になります。
\relax
がないと、次に続く別のトークンが整数式の一部として解釈されてしまう恐れがあります。
\newcount\result
\result=\numexpr 5 + 3 \relax
\the\result
- 上記マクロは
12
や3
という整数値を返します。
\numexpr
は本来は計算用マクロなので以下のように使えます。
% 加算
\numexpr 12 + 3 \relax \par % -> 15
% 減算
\numexpr 12 - 3 \relax \par % -> 9
% 乗算
\numexpr 12 * 3 \relax \par % -> 36
% 除算(商のみ)
\numexpr 12 / 3 \relax \par % -> 4
2.2 number → character
目的
12
(number) を "12"
(文字列) として出力あるいは取得したい
方法
\the\hoge
と書くと、\hoge
(number) を文字列に展開してくれます。
% #1 は "12" や "3" のような数字文字列を想定
\def\CharacterToNumber#1{%
\numexpr #1\relax
}
\the\CharacterToNumber{12} % -> “12”
\the\CharacterToNumber{3} % -> “3”
- 上記マクロは
"12"
や"3"
という文字列を返します。\the
で数値を文字列化しています。
2.3 number → counter
目的
number を任意のカウンタに代入したい
方法
numberはそのままcounterに代入できます。
\newcounter{mycounter}
\newcommand{\NumberToCounter}[1]{%
\setcounter{mycounter}{\numexpr#1\relax}
}
\NumberToCounter{3}
\arabic{mycounter} % -> 3
\NumberToCounter{12}
\arabic{mycounter} % -> 12
2.4 counter → number
目的
カウンタの値を number として扱いたい(たとえば演算したい)
方法
\value{mycounter}
とすればいいです。
\newcounter{mycounter}
\setcounter{mycounter}{3}
\value{mycounter} % -> 3
\setcounter{mycounter}{12}
\value{mycounter} % -> 12
2.5 character → counter
目的
"12"
のような数字文字列(あるいは "3"
のような一桁文字列)をカウンタに直接代入したい
方法
-
\newcounter
と\setcounter` で定義します(初期値は0) -
\stepcounter
で簡単に1増加できます
\newcounter{hoge}
\setcounter{hoge}{3}
\Roman{hoge} % => "III"
\setcounter{hoge}{12}
\Roman{hoge} % => "XII"
\stepcounter{hoge}
\Roman{hoge} % => "XIII"
2.6 counter → character
目的
カウンタを文字列として取得したい
方法
\arabic{mycounter}
でアラビア数字で出力できます。
\newcounter{mycounter}
\begin{document}
\setcounter{mycounter}{3}
\arabic{mycounter}
\setcounter{mycounter}{12}
\arabic{mycounter}
3. まとめ
TeX で整数を扱うにあたって、次の3要素をしっかり区別するとマクロの設計が理解しやすくなります。
-
character:
"12"
,"3"
などの数字文字列 -
number: TeX 内部の整数。
\numexpr
などで演算できる -
counter:
\newcounter
で定義、\setcounter
で更新される
そして、これらを相互に変換する基本的な流れは下記のようになります。
-
character → number
\numexpr <string> \relax
-
number → character
\the <number>
-
number → counter
\setcounter{<number>}
-
counter → number
\value{<counter_name>}
-
character → counter
\setcounter{<string>}
-
counter → character
\arabic{<counter_name>}
ここまで読んでいただき、ありがとうございました。
Discussion