在 C 中,如何创建一个函数,给定一个字符串文字作为参数,returns 一个 char*? (不在堆上分配新内存)
In C, how to create a function that, given a string literal as a parameter, returns a char*? (Without allocating new memory on the heap)
期望的结果:
utilityfun("&xxx")
必须 return 一个指向 "xxx".
的指针
utilityfun("xxx")
必须 return 指向“*xxx”的指针。
#include <stdio.h>
#include <string.h>
char* utilityfun(char *s)
{
if(*s=='&')
return s+1; // this case works fine
else
{
char r[strlen(s)+2];
memset(r,'*',1);
strcpy(r+1,s);
char* p=r;
return p; // !!! p is local to this stack frame!
}
}
void main()
{
char* q=utilityfun("xxx");
printf("%p\n",q);
printf("%s\n",q); // *xxx It seems to work if I use q right way, but...
utilityfun("eee");
printf("%s\n",q); // *eee
}
在堆上分配一个新的字符数组是唯一的方法吗?
我的问题是:作为 utilityfun
实用函数,我不想在每次使用它时都释放它之外的内存。有办法吗?
您可以定义一个 public 变量,然后在函数中填充并 return 它:
char *out;
char* utilityfun(char *s)
{
if(*s=='&')
return s+1; // this case works fine
else
{
// char r[strlen(s)+2]; // You cannot use of non-constant array length
char *r = (char*)malloc(strlen(s) + 2);
memset(r,'*',1);
strcpy(r+1,s);
strcpy(out, r); // Instead of char* p=r; use of this
free(r); // Then free r
return out;
}
}
在 main 函数中,分配它以获得正确的大小:
void main()
{
char *input = "xxx";
out = (char*)malloc(strlen(input) + 1);
char* q=utilityfun(input);
printf("%p\n",q);
printf("%s\n",q);
}
鉴于它只需要处理字符串文字……您可以使用宏。
#include <stdio.h>
#define utilityfun(x) utilityfun_("*" x)
char *utilityfun_(char *s) {
if (s[0] == '*' && s[1] == '&') {
return s + 2;
}
return s;
}
int main(int argc, char **argv) {
char *a = utilityfun("eee");
char *b = utilityfun("&fff");
// Prints "a = *eee; b = fff;\n"
printf("a = %s; b = %s;\n", a, b);
}
这是一个非常难看的 hack,但它不会在运行时分配内存。它只适用于字符串文字,因为它使用字符串文字连接来避免分配——在 C 中,"abc" "def"
变为 "abcdef"
。这不适用于非文字,例如,"abc" x
不起作用。
我认为 Dietrich 的解决方案最适合我的问题,但这是替代解决方案吗?这种方法有主要缺点吗?
{
static char arr[10];
strncpy(arr,s,9);
if(arr[0]=='&')
{
return arr+1;
}
else
{
memcpy(&arr[1],&arr[0],strlen(s)+1);
arr[0]='*';
return arr;
}
}
期望的结果:
utilityfun("&xxx")
必须 return 一个指向 "xxx".
utilityfun("xxx")
必须 return 指向“*xxx”的指针。
#include <stdio.h>
#include <string.h>
char* utilityfun(char *s)
{
if(*s=='&')
return s+1; // this case works fine
else
{
char r[strlen(s)+2];
memset(r,'*',1);
strcpy(r+1,s);
char* p=r;
return p; // !!! p is local to this stack frame!
}
}
void main()
{
char* q=utilityfun("xxx");
printf("%p\n",q);
printf("%s\n",q); // *xxx It seems to work if I use q right way, but...
utilityfun("eee");
printf("%s\n",q); // *eee
}
在堆上分配一个新的字符数组是唯一的方法吗?
我的问题是:作为 utilityfun
实用函数,我不想在每次使用它时都释放它之外的内存。有办法吗?
您可以定义一个 public 变量,然后在函数中填充并 return 它:
char *out;
char* utilityfun(char *s)
{
if(*s=='&')
return s+1; // this case works fine
else
{
// char r[strlen(s)+2]; // You cannot use of non-constant array length
char *r = (char*)malloc(strlen(s) + 2);
memset(r,'*',1);
strcpy(r+1,s);
strcpy(out, r); // Instead of char* p=r; use of this
free(r); // Then free r
return out;
}
}
在 main 函数中,分配它以获得正确的大小:
void main()
{
char *input = "xxx";
out = (char*)malloc(strlen(input) + 1);
char* q=utilityfun(input);
printf("%p\n",q);
printf("%s\n",q);
}
鉴于它只需要处理字符串文字……您可以使用宏。
#include <stdio.h>
#define utilityfun(x) utilityfun_("*" x)
char *utilityfun_(char *s) {
if (s[0] == '*' && s[1] == '&') {
return s + 2;
}
return s;
}
int main(int argc, char **argv) {
char *a = utilityfun("eee");
char *b = utilityfun("&fff");
// Prints "a = *eee; b = fff;\n"
printf("a = %s; b = %s;\n", a, b);
}
这是一个非常难看的 hack,但它不会在运行时分配内存。它只适用于字符串文字,因为它使用字符串文字连接来避免分配——在 C 中,"abc" "def"
变为 "abcdef"
。这不适用于非文字,例如,"abc" x
不起作用。
我认为 Dietrich 的解决方案最适合我的问题,但这是替代解决方案吗?这种方法有主要缺点吗?
{
static char arr[10];
strncpy(arr,s,9);
if(arr[0]=='&')
{
return arr+1;
}
else
{
memcpy(&arr[1],&arr[0],strlen(s)+1);
arr[0]='*';
return arr;
}
}