각 유형에 대한 요약 할당 자와 할당 취소 자. 타입 정의
typedef struct foo
{
int x;
double y;
char *z;
} Foo;
을 감안하면 할당 기능
Foo *createFoo(int x, double y, char *z)
{
Foo *newFoo = NULL;
char *zcpy = copyStr(z);
if (zcpy)
{
newFoo = malloc(sizeof *newFoo);
if (newFoo)
{
newFoo->x = x;
newFoo->y = y;
newFoo->z = zcpy;
}
}
return newFoo;
}
복사 기능
Foo *copyFoo(Foo f)
{
Foo *newFoo = createFoo(f.x, f.y, f.z);
return newFoo;
}
과 역할 당기 기능을 차례로 createFoo()
가를 부르는
void destroyFoo(Foo **f)
{
deleteStr(&((*f)->z));
free(*f);
*f = NULL;
}
주를 만들 copyStr()
함수는 문자열을 저장하고 문자열의 내용을 복사하는 역할을합니다. copyStr()
이 실패하고 NULL을 반환하면 newFoo
은 메모리 할당을 시도하지 않고 NULL을 반환합니다. 마찬가지로 destroyFoo()
은 구조체의 나머지 부분을 해제하기 전에 z의 메모리를 삭제하는 함수를 호출합니다. 마지막으로 destroyFoo()
은 f의 값을 NULL로 설정합니다.
핵심 요소는 멤버 요소에도 메모리 관리가 필요한 경우 할당 자 및 할당 취소자가 책임을 다른 함수에 위임한다는 것입니다. 당신의 유형은 더 복잡 그래서, 당신과 같이 그 할당자를 다시 사용할 수 있습니다 :
typedef struct bar
{
Foo *f;
Bletch *b;
} Bar;
Bar *createBar(Foo f, Bletch b)
{
Bar *newBar = NULL;
Foo *fcpy = copyFoo(f);
Bletch *bcpy = copyBar(b);
if (fcpy && bcpy)
{
newBar = malloc(sizeof *newBar);
if (newBar)
{
newBar->f = fcpy;
newBar->b = bcpy;
}
}
else
{
free(fcpy);
free(bcpy);
}
return newBar;
}
Bar *copyBar(Bar b)
{
Bar *newBar = createBar(b.f, b.b);
return newBar;
}
void destroyBar(Bar **b)
{
destroyFoo(&((*b)->f));
destroyBletch(&((*b)->b));
free(*b);
*b = NULL;
}
물론,이 예제는 회원들이 용기 외부의 수명이없는 것으로 가정합니다. 그렇다고 항상 그런 것은 아니므로 적절하게 인터페이스를 설계해야합니다. 그러나 이것은 당신에게해야 할 일의 맛을 주어야합니다.
이렇게하면 메모리 관리에서 전투의 80 % 인 일관되고 잘 정의 된 순서로 개체 메모리를 할당 및 할당 취소 할 수 있습니다. 나머지 20 %는 모든 할당 자 호출이 해제 코드에 의해 균형을 이루고 있는지 확인합니다. 내가 올바른 유형을 전달하고 있습니다 있도록
편집
delete*
함수 호출을 변경.
이 오랜 시간 C 코더는 C++로 전환되어 문제가 해결되었습니다. –
@Neil Butterworth : 문제가 훨씬 악화되었습니다. – sharptooth
@sharptooth : C++에 대한 팬이 아니지만, 전체 메모리 관리 문제를 해결해줍니다. 물론 어려운 것들을 떠난다. :-) – JesperE