本来我在看《C和指针》,刚好做到一个题是这样的
然后我就去写了一下,然后找了个答案对对,是这样的
#include <stdio.h>
#include <stdlib.h>
#include <string.h> // For memset
void* my_calloc(size_t num, size_t size)
{
size_t total_size = num * size;
void *ptr = malloc(total_size);
// Check if malloc succeeded
if (ptr == NULL)
{
return NULL;
}
memset(ptr, 0, total_size);
return ptr;
}
int main()
{
int *arr = (int*) my_calloc(5, sizeof(int));
if (arr == NULL)
{
printf("Memory allocation failed.\n");
return 1;
}
for (int i = 0; i < 5; i++)
{
printf("%d ", arr[i]);
}
printf("\n");
free(arr);
return 0;
}
然后发现里面有个定义数据类型的size_t,没咋见过,我就去找了一下相关的资料,包括同类型,下面整理在这。
1.size_t
1.1定义
-
无符号整型:
size_t
是无符号的,这意味着它不表示负数,只能表示零及正数。 -
适应性:
size_t
的大小与平台相关。例如,在 32 位系统上,它通常是 32 位的,而在 64 位系统上,它通常是 64 位的。这样可以确保它足够大以表示系统能够处理的最大内存大小。 -
定义:
size_t
是在<stddef.h>
(C)或<cstddef>
(C++)头文件中定义的。在这些头文件中,它通常被定义为typedef
的一种无符号整型,如unsigned int
或unsigned long
,具体取决于平台的需求。
1.2 使用场景
直接上代码
#include <stdio.h>
#include <stdlib.h>
int main() {
size_t array_size = 10;
int *array = (int*) malloc(array_size * sizeof(int));
if (array == NULL) {
printf("Memory allocation failed.\n");
return 1;
}
// Initialize the array
for (size_t i = 0; i < array_size; i++) {
array[i] = i;
}
// Print the array
for (size_t i = 0; i < array_size; i++) {
printf("%d ", array[i]);
}
printf("\n");
// Free allocated memory
free(array);
return 0;
}
- 兼容性:
size_t
可以确保处理大于常规整型范围的内存大小或数组索引,特别是在 64 位系统上。 - 安全性:由于
size_t
是无符号的,它不能表示负值,这在处理内存或数组索引时提供了额外的安全性。
2.ptrdiff_t
2.1定义
用于表示两个指针之间的差值,常见于指针运算和数组操作中(即指针算术结果)。它是一个有符号整型,定义在 <stddef.h>。具体的就不介绍了,以后碰见了再写上来。
2.2使用场景
不多废话,直接代码
#include <stdio.h>
int main() {
int array[10];
int *start = &array[0];
int *end = &array[9];
ptrdiff_t difference = end - start; // 计算指针间的差值
printf("The difference between pointers is: %td\n", difference);
return 0;
}
说明一下,在这里,%td
用于打印 ptrdiff_t
类型的值。
3.ssize_t
3.1定义
这个和我之前碰见的那个size_t很像,但是size_t只能表示非负数,这个也可以表示负数,所以一般都用了做错误码。表示函数返回的字节数或错误码。定义在 <unistd.h>(POSIX 标准)。
3.2使用场景
#include <stdio.h>
#include <unistd.h> // For ssize_t and system calls
#include <string.h>
int main() {
char buffer[100];
ssize_t bytes_read = read(STDIN_FILENO, buffer, sizeof(buffer));
if (bytes_read == -1) {
perror("Read failed");
return 1;
}
buffer[bytes_read] = '\0'; // Null-terminate the string
printf("Read %zd bytes: %s\n", bytes_read, buffer);
return 0;
}
在这里,%zd
用于打印 ssize_t
类型的值。
4.intmax_t 和 uintmax_t
4.1 定义
这两个类型分别是有符号和无符号的最大整型,定义在 <stdint.h>,用于表示系统能够支持的最大整数值,提供了跨平台的整数范围保证。
4.2使用场景
#include <stdio.h>
#include <stdint.h>
int main() {
intmax_t max_signed = INTMAX_MAX;
uintmax_t max_unsigned = UINTMAX_MAX;
printf("Maximum signed intmax_t: %jd\n", max_signed);
printf("Maximum unsigned uintmax_t: %ju\n", max_unsigned);
return 0;
}
在这里,%jd 用于打印 intmax_t 类型的值,%ju 用于打印 uintmax_t 类型的值。
5.uintptr_t 和 intptr_t
5.1 定义
uintptr_t 是一个无符号整型,足够大以存储指针;intptr_t 是一个有符号整型,用于存储指针。定义在 <stdint.h>。
5.2 使用场景
#include <stdio.h>
#include <stdint.h>
int main() {
int value = 42;
int *ptr = &value;
uintptr_t int_ptr = (uintptr_t)ptr; // 将指针转换为 uintptr_t
printf("Pointer as uintptr_t: %ju\n", (uintmax_t)int_ptr);
int *restored_ptr = (int *)int_ptr; // 将 uintptr_t 转回指针
printf("Restored value: %d\n", *restored_ptr);
return 0;
}
在这里,%ju 用于打印 uintptr_t 类型的值,%d 用于打印整型值。