我一直在研究初学者C的问题,以尝试学习C的基础知识。我注意到下面的问题将从最后一个字符串起飞的索引开始,并将完成该字符串,但是我正在尝试要做的就是将两个字符串连接在一起。
有人能指出我正确的方向吗?我正在尝试不重新分配学习xp而这样做。
char *string_dup(char *src)
{
int len = strlen(src);
char *src2 = malloc(len + 1);
int i;
for(i = 0; i < len; i++){
*(src2 + i) = *(src + i);
}
*(src2 + len )='\0';
return src2;
}
void *resize_memory(void *ptr, int old_size, int new_size)
{
char *d = (char*)ptr;
d = malloc(new_size);
}
char *url = string_dup("http://");
char *path = string_dup("website.com/");
int url_length = string_length(url);
int path_length = string_length(path);
int new_length = url_length - 1 + path_length;
char *new_url = resize_memory(url, url_length, new_length);
char *p = new_url + url_length;
while (*path != '\0') {
*p = *path;
p++;
path++;
}
printf("Full path string: %s\n", new_url);
答案 0 :(得分:2)
OP的代码出现问题:
大小错误
假设string_length()
就像strlen()
。
// int new_length = url_length - 1 + path_length;
int new_length = url_length + 1 + path_length;
调整大小无效
void *resize_memory(void *ptr, int old_size, int new_size) {
char *d = (char*)ptr; // assign `d`
d = malloc(new_size); // Why re-assigned `d`???
// No use of old_size, new_size
// No copying of existing data
// No freeing of old allocation
}
我希望类似
// return failure status
bool resize_memory(void **ptr_addr, size_t old_size, size_t new_size) {
void *new_ptr = NULL;
if (new_size > 0) {
new_ptr = malloc(new_size);
if (new_ptr) { // Out of memory, leave *ptr_addr alone
return true;
}
size_t min_size = old_size < new_size ? old_size : new_size;
memcpy(new_ptr, *ptr_addr, min_size);
}
free(*ptr_addr);
*ptr_addr = new_ptr;
return false;
}
如何通过分配来连接带有realloc()
的字符串。
示例代码:
// s1, s2 may be NULL. A NULL is treated as if ""
char *JoinStrings(const char *s1, const char *s2) {
size_t len1 = s1 ? strlen(s1) : 0;
size_t len2 = s2 ? strlen(s2) : 0;
char *joined = malloc(len1 + len2 + 1);
if (joined) {
memcpy(joined, s1, len1);
memcpy(joined + len1, s2, len2);
joined[len1 + len2] = '\0';
}
return joined;
}
或通过snprintf()
char *JoinStrings(const char *s1, const char *s2) {
size_t sz = (s1 ? strlen(s1) : 0) + (s2 ? strlen(s2) : 0) + 1;
char *joined = malloc(sz);
if (joined) {
int len = snprintf(joined, sz, "%s%s", s1, s2);
assert(len >= 0 && (unsigned) len < sz); // Failure is very unexpected here.
}
return joined;
}
要像(* s1)+ = s2那样串联
// *s1 is a prior allocated string, or NULL
void ConcatenateString(char **s1, const char *s2) {
char *joined = JoinStrings(*s1, s2);
free(*s1);
*s1 = joined;
}
答案 1 :(得分:0)
尝试类似
char *url = string_dup("http://");
char *path = string_dup("website.com/");
size_t sTotal = strlen(url) + strlen(path) + 1u;
char *pStr = malloc(sTotal);
snprintf(pStr, sTotal, "%s%s", url, path);
free(url);
free(path);
答案 2 :(得分:0)
我玩了一段时间您的代码,然后提出了这个解决方案。这样,您就可以摆脱该string_dup()
函数,并创建一个可以分配/分配新字符串并为现有字符串添加更多数据的函数。
int
append_string(char **append_to, char *append_this) {
char *tmp;
// You might want to check that append_this is not
// NULL...
if (*append_to == NULL) {
*append_to = malloc(strlen(append_this) + 1);
strcpy(*append_to, append_this);
}
else {
// Some data already exists on the append_to buffer...
//
// If you want to only use malloc() then make a temporary
// storage area and copy the append_to string there
//
if ((tmp = malloc(strlen(*append_to) + 1)) == NULL)
return -1;
strcpy(tmp, *append_to);
// Free up and re-allocate append_to.
//
free(*append_to);
*append_to = malloc(strlen(tmp) + strlen(append_this) + 1);
if (! append_to) {
fprintf(stderr, "Malloc error...");
exit(EXIT_FAILURE);
}
// Do it with realloc
//
// No temporary buffer required:
//
// *append_to = realloc(
// *append_to,
// (strlen(append_to) + strlen(*append_this) + 1)
// );
// if (! eppend_to) ...realloc error
// Copy the data to the buffer and clean up.
//
sprintf(*append_to, "%s%s", tmp, append_this);
free(tmp);
}
}
/* In your main() or whatever... */
char *url = NULL;
char *path = NULL;
// Since url and path are both NULL the
// append string function will act like
// your string_dup() function...
append_string(&url, "http://");
append_string(&path, "website.com/");
// And not that url is not null it will be
// resized and the path appended.
append_string(&url, path);
fprintf(stdout, "URL: %s\n", url);
// Some housekeeping....
if (url) free(url);
if (path) free(path);
}
希望它有用,我知道它与您最初拥有的还相去甚远,但我想我会继续玩下去!