标准库中的字符串方法已经定义了语义。如果生成一个char
包含各种值的数组,并将指针传递给数组或其一部分,则其行为以 NUL 字节定义的方法必须以与标准定义的相同方式搜索 NUL 字节。
人们可以定义自己的字符串处理方法,该方法使用更好的字符串存储形式,并简单地假装标准库与字符串相关的函数不存在,除非必须将字符串传递给fopen
. 这种方法的最大困难是,除非使用不可移植的编译器功能,否则不可能使用内联字符串文字。而不是说:
ns_output(my_file, "This is a test"); // ns -- new string
人们不得不说更像:
MAKE_NEW_STRING(this_is_a_test, "This is a test");
ns_output(my_file, this_is_a_test);
其中宏MAKE_NEW_STRING
将创建一个匿名类型的联合,定义一个名为 的实例this_is_a_test
,并适当地初始化它。由于许多字符串将具有不同的匿名类型,因此类型检查将要求字符串是包含已知数组类型成员的联合,并且应为期望字符串的代码提供该成员的指针,可能使用如下内容:
#define ns_output(f,s) (ns_output_func((f),(s).stringref))
可以以这样的方式定义类型以避免对stringref
成员的需要并且让代码只接受void*
,但是 stringref 成员本质上将执行静态鸭子类型(只有具有stringref
成员的东西才能被赋予这样的宏) 并且还可以允许对自身的类型进行类型检查stringref
)。
如果可以接受这些约束,我认为可以编写几乎在所有方面都比以零结尾的字符串更有效的代码;问题是这些优势是否值得麻烦。