2013-02-17 17 views
5

tôi cần sự giúp đỡ của bạn!bản sao sâu của cấu trúc với điểm trỏ trong C

Tôi muốn sao chép một cấu trúc như thế này:

typedef struct PackageObject_s { 
    long **vertex;   // vertices 
    long num_vertex;  // count of vertices 
    long objectType;  // 
    REAL r;    // 
    long bottom[3];  // bounding box bottom vector 
    long top[3];   // bounding box top vector 
    long *start;   // 
    REAL coverage;  // 
} PackageObject __attribute__ ((aligned)); 

tôi thử nó như thế này:

static inline void PackageObject_copy(PackageObject *dst, const PackageObject *src) { 

    dst->num_vertex = src->num_vertex; 
    dst->objectType = src->objectType; 
    dst->r   = src->r; 
    vec_assign3l(dst->bottom, src->bottom); 
    vec_assign3l(dst->top, src->top); 

    // TODO copy **vertex ??? 

    dst->coverage = src->coverage; 
    dst->coverage = src->coverage; 
} 

Làm thế nào tôi có thể giải quyết này?

Cảm ơn bạn trước sự giúp đỡ của bạn !!

CẬP NHẬT - giải pháp của tôi cho deepcopy của vertex - thx cho tất cả sự giúp đỡ:

dst->vertex = (long *)malloc(dst->num_vertex * 3 * sizeof(long)); 
for (long i=0; i < src->num_vertex; i++) { 
    dst->vertex[i] = (long)malloc(3*sizeof(long)); 
    memcpy(dst->vertex[i],src->vertex[i],3 * sizeof(long)); 
} 
+0

bạn cần phải sao chép ** đỉnh?! – amrfaissal

+0

Cảm ơn mọi câu trả lời (@Sparky, @Foon, @eznme). Tôi đã nhận nó :-)
'dst-> vertex = (dài *) malloc (dst-> num_vertex * 3 * sizeof (dài)); cho (dài i = 0; i < src-> num_vertex; i ++) {dst-> đỉnh [i] = (dài) malloc (3 * sizeof (dài)); memcpy (dst-> đỉnh [i], src-> đỉnh [i], 3 * sizeof (dài)); } ' – romi1013

Trả lời

2

Tôi sẽ giả định rằng các đỉnh không được chia sẻ giữa các đối tượng. Đó là, chúng thuộc về cấu trúc được đề cập.

Có hai trường hợp chính để xem xét:

1. Copying into a new object 
2. Copying into an existing object 

Sao chép vào đối tượng mới là đơn giản.

1a. Allocate space for <num_vertex> pointers. 
1b. Allocate space for each vertex. 
2a. Copy <num_vertex> pointers from source to destination. 
2b. Copy <num_vertex> vertices from source to destination. 

Sao chép vào đối tượng hiện có giống như sao chép vào đối tượng mới ngoại trừ việc bạn phải thực hiện thao tác sau trước.

0a. Loop through each element of <vertex> and free the vertex. 
0b. Free the array of vertex pointers. 
1. Follow the steps for copying into a new object. 

Hy vọng điều này sẽ hữu ích.

2

Original câu trả lời:

Giả sử điểm đỉnh vào một mảng các đỉnh, và rằng mỗi vertice chứa 3 chờ đợi (x , y, z):

dst->vertex = (long **)malloc(dst->num_vertex * 3 * sizeof(long); 
memcpy(dst,src,dst->num_vertex * 3 * sizeof(long)); 

cập nhật vì tôi nhận ra điều này có thể làm việc nhưng không sạch hoặc đặc biệt là an toàn Như tôi đã đề cập trong bình luận, mã sẽ sạch hơn nếu bạn có

typedef struct vertextag { 
    long x; 
    long y; 
    long z; 
} vertex_type; 

Và sau đó đã làm: dst-> đỉnh = (vertex_type *) malloc (dst-> num_vertex * sizeof (vertex_type); memcpy (dst, src, dst-> num_vertex * sizeof (vertex_type));

+0

Xem xét một số câu trả lời khác, tôi đã không nghĩ về hai trường hợp. Câu trả lời này giả định rằng mảng đỉnh là duy nhất cho mỗi đối tượng (hoặc bạn sẽ không thực sự cần phải làm sâu sắc nó). Nó cũng giả định rằng dst là một con trỏ hoàn toàn mới (nhưng nó trỏ đến một bộ nhớ hợp lệ mà bạn hoặc malloc'd hoặc được tạo ra trên ngăn xếp); nếu nó không phải là một đối tượng hoàn toàn mới, bạn muốn đi theo cách tiếp cận của Sparky. Do lưu ý rằng bạn nên kiểm tra xem nếu dst == src nếu dst không được đảm bảo là một đối tượng hoàn toàn mới hoặc ít nhất là tài liệu trong hàm không làm điều đó, nếu không bạn sẽ bị rò rỉ bộ nhớ. – Foon

+0

Mã của bạn có lẽ sẽ sạch hơn nếu bạn có cấu trúc vertex_type {long x, long y, long z)} mà bạn sẽ sử dụng thay vì dài [3] cho các hộp giới hạn và sẽ sử dụng như * vertex_type thay vì dài **; trong trường hợp này, bạn sẽ thực hiện (vertex_type *) malloc (dst-> num_vertex * sizeof (vertex_type); – Foon

+0

Thats right.Mảng vertex là duy nhất cho mỗi đối tượng, mỗi đối tượng đều có các đỉnh num_vertex Mỗi Vertex ist a 3D Coordinate (dài Vì vậy, giải pháp đầu tiên của bạn không làm việc.Nếu tôi thay đổi một đỉnh, tôi thay đổi nó với giải pháp này trong cả hai đối tượng. – romi1013

1

Nó phụ thuộc vào việc các mảng đỉnh nên thuộc về đối tượng bạn đang cố gắng sao chép hoặc cho dù nó được chia sẻ giữa nhiều đối tượng. Cả hai cách tiếp cận được sử dụng trong thực tế, tùy thuộc vào tình hình (mảng phải được sao chép nếu các đỉnh có thể được thay đổi riêng biệt cho đối tượng sao chép). Bạn phải chọn cái nào trong số chúng có ý nghĩa đối với ứng dụng bạn đang phát triển.

Nếu mảng có thể được chia sẻ bởi các đối tượng trỏ đến chúng, chỉ cần sao chép con trỏ.

dst->vertex = src->vertex; 

Nếu mỗi đối tượng có đỉnh riêng của họ (để họ có thể được thay đổi riêng cho đối tượng sao chép) sau đó bạn phải phân bổ và sao chép các mảng và nơi con trỏ được lưu trữ và thiết lập một con trỏ đến nơi đó vào đối tượng sao chép.

long* vertexCopy = malloc(howmanybytes); 
memcpy(vertexCopy, *src->vertex, howmanybytes); 
long** holder = malloc(sizeof(void*)); 
holder[0] = vertexCopy; 
dst->vertex = holder;