Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is shallow copy sufficient for structures with char[]?

I have a structure containing character arrays with no any other member functions. I am doing assignment operation between two instances of these structures. If I'm not mistaken, it is doing shallow copy. Is shallow copy safe in this case?

I've tried this in C++ and it worked but I would just like to confirm if this behavior is safe.

like image 487
jasonline Avatar asked Feb 11 '10 01:02

jasonline


People also ask

What is the maximum size of char array in C?

The maximum allowable array size is 65,536 bytes (64K). Reduce the array size to 65,536 bytes or less.

Is struct shallow copy?

The copy that you get from an assignment statement with a structure variable is a bit-for-bit copy, also called a shallow copy.

What are problems with shallow copy?

The problem with the shallow copy is that the two objects are not independent. If you modify the one object, the change will be reflected in the other object. A deep copy is a fully independent copy of an object. If we copied our object, we would copy the entire object structure.


1 Answers

If by "shallow copy", you mean that after assignment of a struct containing an array, the array would point to the original struct's data, then: it can't. Each element of the array has to be copied over to the new struct. "Shallow copy" comes into the picture if your struct has pointers. If it doesn't, you can't do a shallow copy.

When you assign a struct containing an array to some value, it cannot do a shallow copy, since that would mean assigning to an array, which is illegal. So the only copy you get is a deep copy.

Consider:

#include <stdio.h>

struct data {
    char message[6];
};

int main(void)
{
    struct data d1 = { "Hello" };
    struct data d2 = d1; /* struct assignment, (almost) equivalent to
                            memcpy(&d2, &d1, sizeof d2) */

    /* Note that it's illegal to say d2.message = d1.message */

    d2.message[0] = 'h';
    printf("%s\n", d1.message);
    printf("%s\n", d2.message);
    return 0;
}

The above will print:

Hello
hello

If, on the other hand, your struct had a pointer, struct assignment will only copy pointers, which is "shallow copy":

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

struct data {
    char *message;
};

int main(void)
{
    struct data d1, d2;
    char *str = malloc(6);
    if (str == NULL) {
        return 1;
    }
    strcpy(str, "Hello");
    d1.message = str;
    d2 = d1;

    d2.message[0] = 'h';
    printf("%s\n", d1.message);
    printf("%s\n", d2.message);
    free(str);
    return 0;
}

The above will print:

hello
hello

In general, given struct T d1, d2;, d2 = d1; is equivalent to memcpy(&d2, &d1, sizeof d2);, but if the struct has padding, that may or may not be copied.

Edit: In C, you can't assign to arrays. Given:

int data[10] = { 0 };
int data_copy[10];

data_copy = data;

is illegal. So, as I said above, if you have an array in a struct, assigning to the struct has to copy the data element-wise in the array. You don't get shallow copy in this case: it doesn't make any sense to apply the term "shallow copy" to a case like this.

like image 63
Alok Singhal Avatar answered Oct 13 '22 00:10

Alok Singhal