正如手册所述l3intarray
,对于命令\intarray_new:Nn
,变量分配始终是全局的,并且数组的大小是固定的,必须在初始化时给出。
这会导致一个问题,例如我的代码定义
\newcommand{\mycommand}[1]{
\intarray_new:Nn\g_myarray{#1}
% Some useful operations with it here
}
然后当我\mycommand
多次使用时,它会引发错误。但是我不能将初始化放在外面,因为这{<size>}
意味着会发生变化。而且我不想创建一个巨大的数组来满足所有情况。
现在,我有了这样的解决方案,
\newcommand{\mycommand}[1]{
\let\g_myarray\undefined
\intarray_new:Nn\g_myarray{#1}
% Some useful operations with it here
}
有没有更好的方法来做到这一点,或者我的方法是唯一可行的方法?
答案1
当你执行 时\intarray_new:Nn
,会加载字体;具体加载哪种字体并不重要,因为它不用于排版,而只是为了利用 TeX 的一个特性。摘自 TeXbook,第 277-278 页
\fontdimen
当分配一个值时,<number>
必须为正数,并且不大于字体度量信息文件中的参数数量,除非该字体信息刚刚被加载到 TeX 的内存中;在后一种情况下,您可以增加参数的数量(参见附录 F)。
然后\intarray_new:Nn
分配\fontdimen
第二个参数中指定的参数数量。之后无法更改参数数量,如上面的引文所述。
加载字体时,其度量信息及其\fontdimen
参数会存储在内存中,无法删除。如今字体内存量很大;TeX Live 2022 设置
% Words of font info for TeX (total size of all TFM files, approximately).
% Must be >= 20000 and <= 147483647 (without tex.ch changes).
font_mem_size = 8000000
% Total number of fonts. Must be >= 50 and <= 9000 (without tex.ch changes).
font_max = 9000
虽然加载多个字体intarrays
在字体数量上应该不是什么大问题,但在字体内存大小上可能是一个大问题。让我们看看。对于一个空的 LaTeX 文件,我得到
512287 words of font info for 32 fonts, out of 8000000 for 9000
如果我添加\intarray_new:Nn \g_tmpa_intarray { 65536 }
,数字就变成
578116 words of font info for 33 fonts, out of 8000000 for 9000
差异是 65829,您会发现分配超过 8000000 个参数将需要增加font_mem_size
。很难想象需要如此庞大的数组大小的应用程序。
您的取消定义策略\g_myarray
(顺便说一句,这与命名标准不一致)迟早会导致内存填满。
分配
\intarray_new:Nn \g_youthdoo_myarray_intarray { <number> }
具有足够大的<number>
条目,足以满足您的应用程序的需求。
您可能还想分配
\int_new:N \g_youthdoo_myarray_int
因此,当您设置值时,\g_youthdoo_myarray_intarray
您还可以设置最高合法索引,\g_youthdoo_myarray_int
当您检索值时,您可以检查其索引是否在当前设置的范围内。