Size of predefined/assigned char[], naming conventions, easily copying a struct and fetching function address with ampersand
How to find the size of a predefined char[] variable that holds a string? Should sizeof be enough? I don't want to use strlen() since a '\0' character may occur in the string, and for optimization reasons. E.g.:
char str[] = "Hello \x45\x10\x00 World!";
What do you do when there're initials in the identifier? E.g. GetURLParameters(). I thought of adding an underscore: GetURL_Parameters(). What is the convention for this situation?
How can I easily copy values 开发者_C百科to the fields of a struct that is pointed by a variable/pointer? For example, I would like to do something similar to:
struct { int bar1; char* bar2; callback bar3; } *foo = NULL; foo = malloc(sizeof *foo); *foo = { 0, "Hello World!", myFunc }; // This is wrong
Why programmers sometimes use an ampersand to assign an address of a function to a function pointer? E.g.:
void (*callback)(void); callback = &myFunc;
(Sorry, but I can't edit well my post. It looks different when I edit, and when it's shown to you)
- If it's a
char[]
and not achar *
,sizeof()
will give you the array size (which isstrlen() + 1
for nul-terminated strings). If you need to work extensively with strings (especially ones that may have the'\0'
character in them and/or may not be nul-terminated) you should consider using a string library. It will make your life much easier. - Whatever you want. I personally never use capital letters in identifiers, because I think
MixedCaseIdentifiers
are ugly. There is no convention for naming identifiers, only conventions that some people like. Use whatever looks best to you (and your team). You can do this:
struct s { int bar1; char* bar2; callback bar3; }; struct s *foo = NULL; static struct s default = { 0, "Hello, world!", myFunc }; foo = malloc(sizeof *foo); *foo = s;
My standards-fu is failing me, so I'm not sure why this works (or even if it does absolutely) but I believe it does. If it doesn't work, you just need to make an
init
function that sets all the fields to their default values.- Consistency. When assigning an address to a pointer, it's normally necessary, i.e.
int i = 5, *j = &i;
so even though it's not strictly necessary for function pointers, some people like to do it so that all pointer assignments look the same. It's just aesthetics.
However, in the future, most of these questions are unrelated to each other. You shouldn't group four unrelated questions into one giant monster question, but instead ask them separately. It'll make you take more time for each one, and each will come out more coherently so we'll be able to give you better answers (and you'll learn more).
sizeof
is good enough for thisMatter of taste. I don't use capitals in identifiers at all (unless they are global constants)
You can do this:
struct foo { int a; char *b; } bar; bar = (struct foo){0, "Hello"};
To make it explicit, although it is not necessary, if
myFunc
is a function.
If you want to copy values from one struct to another, you can do this:
typedef struct {
int bar1;
char* bar2;
int (*callback)(int);
} mystruct;
char str[] = "Hello \x45\x10\x00 World!";
int main() {
mystruct* foo = (mystruct*)malloc(sizeof(mystruct));
mystruct* foo2 = (mystruct*)malloc(sizeof(mystruct));
foo->bar1 = 10;
foo->bar2 = "hi";
printf("foo->bar1 = %d, foo->bar2 = %s\n",foo->bar1,foo->bar2);
memcpy(foo2,foo,sizeof(*foo));
printf("foo2->bar1 = %d, foo2->bar2 = %s\n",foo2->bar1,foo2->bar2);
free(foo);
free(foo2);
return 0;
}
Output:
---------- Capture Output ----------
> "c:\windows\system32\cmd.exe" /c c:\temp\temp.exe
foo->bar1 = 10, foo->bar2 = hi
foo2->bar1 = 10, foo2->bar2 = hi
> Terminated with exit code 0.
In general, the number of elements in an array is given by the expression
sizeof arr / sizeof arr[0]
(orsizeof arr / sizeof *arr
). Thesizeof
operator returns the size of the array in bytes, not the number of elements, so you must divide the number of bytes in the array by the number of bytes in an individual element. However, sincesizeof char == 1
by definition, you can get the number of elements in a char array with justsizeof arr
. Note that the expressionarr
must be an array type, not a pointer type (for example, ifarr
was passed as a function parameter typedT arr[]
, then it's a pointer type, andsizeof
will give you the number of bytes in the pointer, not the array itself).There a number of conventions, none of which are really better than the others. Which convention you pick doesn't matter as long as you use it consistently.
C89 doesn't support compound literals like that. C99 does, and it should look something like
*foo = (struct s) {0, "Hello, World", myfunc};
(assuming you add a tags
to your struct definition). However, I'm not that familiar with C99 features, so don't take that as gospel.Habit. In practice it does nothing (a function designator is implicitly converted to a pointer to a function under the usual conversion rules anyway).
2 I use the c# recommendations
If 2 initials then all caps, otherwize only initial cap. Examples
DSPointer, FtpServer, getHDSeekTime, sendSmtpMessage
精彩评论