简体   繁体   中英

How to assign string into char* pointer?

#include <stdio.h>

struct Analysis {
    int lnlen;   
    int arr[2]; 
    char* name;
};

int main()
{
    struct Analysis ana_space[2];
    char *ptr = (void*) &ana_space;

    ana_space[0].lnlen = 0;
    ana_space[0].arr[0] = 1;
    ana_space[0].arr[1] = 2;
    ana_space[0].name = "Peter";

    printf("\n%d\n", *ptr);     // print 0;

    *ptr = 10;                  // how to use memcpy here;

    printf("\n%d\n", *ptr);     // print 10;

    ptr = ptr + sizeof(int);    // advance pointer by int;

    printf("\n%d\n", *ptr);     // print 1;  

    ptr = ptr + 2*sizeof(int);  // advance pointer by 2 ints;

    printf("\n%s\n", *ptr);     // print "Peter"; --------------not work

    //*ptr = "Jim";             // how to assign new name "Jim" into that memory;
    return 0;
}

Output:

0

10

1

(null)

I want to use char * as pointer to go through memory address to get some data and also store value into memory.

For int and int array, it works fine, but not for the string.

How to print the string and store new string value into memory?

The code you presented could cause undefined behavior due to padding and representations of types, which are implementation-defined.

After you increment the pointer ptr here:

ptr = ptr + 2*sizeof(int);

the pointer ptr points to the member name of the struct Analysis. If you dereference the pointer ptr, you get the type char and thus a single byte. This byte does not represent a pointer to the string.

The pointer ptr will have to be cast to the type pointer to a pointer to char, and then dereferenced so the correct and full value of the member name will be obtained.

That resulting value is a pointer to the string "Peter" .

ANSI C has a macro called offsetof() found in stddef.h that gives a more sure way of calculating the pointer offset of a member within a struct. Here, we can get the the address of the name member in ana_space[0] directly.

ptr = (char*) &ana_space + offsetof(struct Analysis, name);

This takes out any guess work on padding.

This pointer then has to be properly cast to print the contents of name:

printf("%s\n", *(char**) ptr);

Your approach is not portable. It will be better to use offsetof to make sure that you can reliably point to the addresses of the members of a struct .

int main()
{
    struct Analysis ana_space[2];
    char *ptr = (void*) &ana_space;

    size_t offset1 = offsetof(struct Analysis, arr);
    size_t offset2 = offsetof(struct Analysis, name);

    ana_space[0].lnlen = 0;
    ana_space[0].arr[0] = 1;
    ana_space[0].arr[1] = 2;
    ana_space[0].name = "Peter";

    // advance pointer to point to arr.
    ptr = ptr + offset1;

    // advance pointer to point to name
    ptr = ptr + (offset2-offset1);

    // Cast the pointer appropriately before dereferencing.
    printf("\n%s\n", *(char**)ptr); 

    // how to assign new name "Jim" into that memory;
    *(char**)ptr = "Jim";
    printf("\n%s\n", *(char**)ptr);

    return 0;
}

Your use of:

printf("\n%d\n", *ptr);     // print 0;

*ptr = 10;                  // how to use memcpy here;

printf("\n%d\n", *ptr);     // print 10;

and the expected output is flawed. It works only with little endian systems. I suggest using:

printf("\n%d\n", *(int*)ptr);

*(int*)ptr = 10;

printf("\n%d\n", *(int*)ptr);

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM