最近我用C编写了很多代码,我注意到,在我的程序中花费大部分时间的事情是调整动态数据结构的大小.假设我们有一个包含字符的数组,我想在这个数组的末尾添加一些字符.我这样做:
我只是想知道这是否足够有效.例如,我可以想到像树结构这样的东西,我将数组保存在树的节点中,这样,而不是在追加东西之前将旧元素复制到新数组,我只是将新的malloc'ed元素添加到下一个树的节点并在那里附加字符.这样我就可以避免不必要的复制......
所以这只是以不同方式调整大小的一种方式.我应该寻找其他的东西,还是我只是将旧元素复制到新数组的两倍大小的解决方案?
我正在进行socket编程中的一项任务,我必须在sparc和linux机器之间发送一个文件.在char流中发送文件之前,我必须获取文件大小并告诉客户端.以下是我试图获得尺寸的一些方法,但我不确定哪一个是正确的.
出于测试目的,我创建了一个内容为"test"的文件(空格+(字符串)测试)
方法1 - 使用fseeko()和ftello()
这是我在https://www.securecoding.cert.org/confluence/display/c/FIO19-C.+Do+not+use+fseek()+and+ftell()+to+compute+上找到的方法.+大小+ + a +常规+文件 虽然fssek()有一个问题"将文件位置指示器设置为文件结尾,与fseek(文件,0,SEEK_END)一样,但是对于二进制文件有未定义的行为stream",fseeko()据说解决了这个问题,但它只适用于POSIX系统(这很好,因为我使用的环境是sparc和linux)
fd = open(file_path, O_RDONLY);
fp = fopen(file_path, "rb");
/* Ensure that the file is a regular file */
if ((fstat(fd, &st) != 0) || (!S_ISREG(st.st_mode))) {
/* Handle error */
}
if (fseeko(fp, 0 , SEEK_END) != 0) {
/* Handle error */
}
file_size = ftello(fp);
fseeko(fp, 0, SEEK_SET);
printf("file size %zu\n", file_size);
Run Code Online (Sandbox Code Playgroud)
此方法工作正常,并正确获得大小.但是,它仅限于常规文件.我试图谷歌术语"常规文件"但我仍然不太了解它.我不知道这个功能对我的项目是否可靠.
方法2 - 使用strlen()
自从最大 我的项目中的文件大小是4MB,所以我可以只调用一个4MB的缓冲区.之后,文件被读入缓冲区,我尝试使用strlen来获取文件大小(或更正确的内容长度).由于strlen()是可移植的,我可以使用这种方法吗?代码片段是这样的
fp = fopen(file_path, "rb");
fread(file_buffer, 1024*1024*4, 1, …Run Code Online (Sandbox Code Playgroud) 陷入了最简单的问题.
int *p= (int *)malloc(m*sizeof(int));
p={0}; // this is not correct.
Run Code Online (Sandbox Code Playgroud)
除了使用循环之外,如何将整个数组设置为值0?
在最近切换到c之后,我被告知星期天有一千种方法来引用一个尚未初始化的值并不是一种好的做法,并导致出乎意料的行为.具体来说,(因为我以前的语言将整数初始化为0)我被告知在未初始化时整数可能不等于零.所以我决定把它考验一下.
我编写了以下代码来测试这个声明:
#include <stdlib.h>
#include <stdio.h>
#include <stdbool.h>
#include <assert.h>
int main(){
size_t counter = 0;
size_t testnum = 2000; //The number of ints to allocate and test.
for(int i = 0; i < testnum; i++){
int* temp = malloc(sizeof(int));
assert(temp != NULL); //Just in case there's no space.
if(*temp == 0) counter++;
}
printf(" %d",counter);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
我这样编译它(如果它很重要):
gcc -std=c99 -pedantic name-of-file.c
根据我的教师所说的,我希望temp指向一个随机整数,并且计数器不会经常递增.但是,我的结果将这个假设从水中吹走了:
testnum: || code returns:
2 2
20 20
200 200
2000 2000
20000 20000
200000 …Run Code Online (Sandbox Code Playgroud) gcc 4.5.1 c89
Run Code Online (Sandbox Code Playgroud)
我已经编写了这个源代码,以便我更好地理解malloc和calloc.
我理解,但只是有几个问题.
dev = malloc(number * sizeof *devices);
Run Code Online (Sandbox Code Playgroud)
等于这个calloc.我并不担心清理内存.
dev = calloc(number, sizeof *devices);
Run Code Online (Sandbox Code Playgroud)
与在while循环中执行5次相比,这究竟是什么呢?
dev = malloc(sizeof *devices);
Run Code Online (Sandbox Code Playgroud)
我想第一个和第二个是创建一个指向5结构设备的指针.第三个是创建一个指向结构设备的指针?
我的程序说明了使用valgrind编译和运行的3种不同方法--leak-check = full.
非常感谢任何建议.
#include <stdio.h>
#include <stdlib.h>
struct Devices {
#define MAX_NAME_SIZE 80
size_t id;
char name[MAX_NAME_SIZE];
};
struct Devices* create_device(struct Devices *dev);
void destroy_device(struct Devices *dev);
int main(void)
{
size_t num_devices = 5;
size_t i = 0;
struct Devices *device = NULL;
struct Devices *dev_malloc = NULL;
struct Devices *dev_calloc = NULL;
for(i = 0; …Run Code Online (Sandbox Code Playgroud)