Pointers on C——9 Strings, Characters, and Bytes.5

9.4 Length-Restricted String Functions


The library includes several functions that deal with strings in a different way. This group of functions takes an explicit length argument that limits how many characters can be copied or compared. These functions provide an easy mechanism to prevent unexpectedly long strings from overflowing their destinations.

标准库还包含了一些函数,它们以一种不同的方式处理字符串。这些函数接受一个显式的长度参数,用于限定进行复制或比较的字符数。这些函数提供了一种方便的机制,可以防止难以预料的长字符串从它们的目标数组溢出。


The prototypes for these functions are shown on the next page. Like their unrestricted cousins, the results from strncpy and strncat are undefined if the source and destination arguments overlap.

这些函数的原型如下所示。和它们的不受限制版本一样,如果源参数和目标参数发生重叠,strncpy 和strncat 的结果就是未定义的。


char *strncpy( char *dst, char const *src, size_t len );

char *strncat( char *dst, char const *src, size_t len );

int strncmp( char const *s1, char const *s2, size_t len );


Like strcpy, strncpy copies characters from the source string to the destination array.However, it always writes exactly len characters to dst. If strlen( src ) is less than len, then dst is padded to a length of len with additional NUL characters. If strlen(src ) is greater than or equal to len, then only len characters will be written to dst,and the result will not be NUL‐terminated!

和strcpy 一样, strncpy 把源字符串的字符复制到目标数组。然而,它总是正好向dst 写入len个字符。如果strlen( src )的值小于len , dst 数组就用额外的NUL 字节填充到len 长度。如果strlen( src)的值大于或等于len ,那么只有len 个字符被复制到dst 中。注意!它的结果将不会以NUL 字节结尾。


The result of a call to strncpy might not be a string, because strings must be terminated with a NUL byte. What happens if an unterminated sequence of characters is used where a string is required, for example, as an argument to strlen? The function will be unable to tell that the NUL is missing, so it will continue looking,character by character, until it finds one. It might not find one until hundreds of characters later, and the value returned by strlen will essentially be a random number. Or, the program might crash trying to access memory beyond what was allocated to it.

strncpy 调用的结果可能不是一个字符串,因此字符串必须以NUL字节结尾。如果在一个需要字符串的地方(例如strlen 函数的参数)使用了一个不是以NUL 字节结尾的字符序列,会发生什么情况呢? strlen 函数将无法知道NUL 字节是没有的,所以它将继续进行查找,一个字符接一个字符,直到它发现一个NUL 字节为止。或许它找了几百个字符才找到,而strlen 函数的这个返回值从本质上说是一个随机数。或者,如果函数试图访问系统分配给这个程序以外的内存范围,程序就会崩溃。


This problem only occurs when you create strings with the strncpy function, and then either use them with the str--- functions or print them with the %s format code of printf. Before using the unrestricted functions, you must first ensure that the string is actually NUL‐terminated. For example, consider this code fragment:

这个问题只有当你使用strncpy 函数创建字符串,然后或者对它们使用str开头的库函数,或者在printf 中使用%s 格式码打印它们时才会发生。在使用不受限制的函数之前,你首先必须确定字符串实际上是以NUL 字节结尾的。例如,考虑下面这个代码段:


char buffer[BSIZE];

...

strncpy( buffer, name, BSIZE );

buffer[BSIZE – 1] = '\0';


If the contents of name fit into buffer, the assignment has no effect. If name is too long,though, the assignment ensures that the string in buffer is properly terminated.Subsequent calls to strlen or other unrestricted string functions on this array will work properly.

如采name 的内容可以容纳于buffer 中,最后那个赋值语句没有任何效果。但是,如果name 太长,这条赋值语句可以保证buffer 中的字符串是以NUL 结尾的。以后对这个数组使用strlen 或其他不受限制的字符串函数将能够正确工作。


Although strncat is also a length‐restricted function, it works differently than strncpy. It appends up to len characters from src to the destination string. But strncat always appends a NUL character to the end of the result, and it does not pad the result with NULs like strncpy. Note that the length of the existing string in the destination array is not accounted for by strncat. It can write up to len characters plus a terminating NUL byte regardless of whether the initial contents of the destination argument leave enough room for them.

尽管strncat 也是一个长度受限的函数,但它和strncpy 存在不同之处。它从src 中最多复制len个字符到目标数组的后面。但是, strncat 总是在结果字符串后面添加一个NUL 字节,而且它不会像strncpy 那样对目标数组用NUL 字节进行填充。注意目标数组中原先的字符串并没有算在strncat 的长度中。stmcat 最多向目标数组复制len 个字符(再加一个结尾的NUL 字节),它才不管目标参数除去原先存在的字符串之后留下的空间够不够。


Finally, strncmp compares up to len characters of two strings. If the strings are unequal before or at the lenʹth character, the comparison stops as it would with strcmp. If the first len characters of the strings are equal, value zero is returned.

最后, strncmp 也用于比较两个字符串,但它最多比较len 个字节。如果两个字符串在第len 个字符之前存在不相等的字符,这个函数就像由cmp 一样停止比较,返回结果。如果两个字符串的前len 个字符相等,函数就返回零。


上一章 Pointers on C——9  Strings, Characters, and Bytes.4

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
SQLAlchemy 是一个 SQL 工具包和对象关系映射(ORM)库,用于 Python 编程语言。它提供了一个高级的 SQL 工具和对象关系映射工具,允许开发者以 Python 类和对象的形式操作数据库,而无需编写大量的 SQL 语句。SQLAlchemy 建立在 DBAPI 之上,支持多种数据库后端,如 SQLite, MySQL, PostgreSQL 等。 SQLAlchemy 的核心功能: 对象关系映射(ORM): SQLAlchemy 允许开发者使用 Python 类来表示数据库表,使用类的实例表示表中的行。 开发者可以定义类之间的关系(如一对多、多对多),SQLAlchemy 会自动处理这些关系在数据库中的映射。 通过 ORM,开发者可以像操作 Python 对象一样操作数据库,这大大简化了数据库操作的复杂性。 表达式语言: SQLAlchemy 提供了一个丰富的 SQL 表达式语言,允许开发者以 Python 表达式的方式编写复杂的 SQL 查询。 表达式语言提供了对 SQL 语句的灵活控制,同时保持了代码的可读性和可维护性。 数据库引擎和连接池: SQLAlchemy 支持多种数据库后端,并且为每种后端提供了对应的数据库引擎。 它还提供了连接池管理功能,以优化数据库连接的创建、使用和释放。 会话管理: SQLAlchemy 使用会话(Session)来管理对象的持久化状态。 会话提供了一个工作单元(unit of work)和身份映射(identity map)的概念,使得对象的状态管理和查询更加高效。 事件系统: SQLAlchemy 提供了一个事件系统,允许开发者在 ORM 的各个生命周期阶段插入自定义的钩子函数。 这使得开发者可以在对象加载、修改、删除等操作时执行额外的逻辑。
SQLAlchemy 是一个 SQL 工具包和对象关系映射(ORM)库,用于 Python 编程语言。它提供了一个高级的 SQL 工具和对象关系映射工具,允许开发者以 Python 类和对象的形式操作数据库,而无需编写大量的 SQL 语句。SQLAlchemy 建立在 DBAPI 之上,支持多种数据库后端,如 SQLite, MySQL, PostgreSQL 等。 SQLAlchemy 的核心功能: 对象关系映射(ORM): SQLAlchemy 允许开发者使用 Python 类来表示数据库表,使用类的实例表示表中的行。 开发者可以定义类之间的关系(如一对多、多对多),SQLAlchemy 会自动处理这些关系在数据库中的映射。 通过 ORM,开发者可以像操作 Python 对象一样操作数据库,这大大简化了数据库操作的复杂性。 表达式语言: SQLAlchemy 提供了一个丰富的 SQL 表达式语言,允许开发者以 Python 表达式的方式编写复杂的 SQL 查询。 表达式语言提供了对 SQL 语句的灵活控制,同时保持了代码的可读性和可维护性。 数据库引擎和连接池: SQLAlchemy 支持多种数据库后端,并且为每种后端提供了对应的数据库引擎。 它还提供了连接池管理功能,以优化数据库连接的创建、使用和释放。 会话管理: SQLAlchemy 使用会话(Session)来管理对象的持久化状态。 会话提供了一个工作单元(unit of work)和身份映射(identity map)的概念,使得对象的状态管理和查询更加高效。 事件系统: SQLAlchemy 提供了一个事件系统,允许开发者在 ORM 的各个生命周期阶段插入自定义的钩子函数。 这使得开发者可以在对象加载、修改、删除等操作时执行额外的逻辑。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值