[데이터 구조] 단 방향 링크
불 연속 메모리 공간 인 만큼 각 요 소 를 방문 하려 면 지침 을 통 해 찾 아야 합 니 다.링크 구조 에 서 는 데이터 필드 와 포인터 필드 를 정의 해 야 합 니 다.
1. 단 방향 링크 의 데이터 구조
typedef struct _Node
{
int value;
struct _Node *pnext;
}Node;
2. 헤더 가 없 는 단 방향 링크 만 들 기
void createList(Node **ppListNode, int value)
{
Node *pListNode = NULL;
pListNode = (Node *)malloc(sizeof(Node));
assert(pListNode != NULL);
pListNode->value = value;
pListNode->pnext = NULL;
*ppListNode = pListNode;
return;
}
3. 링크 끝 에 요소 추가
이상 상황: 링크 가 존재 하지 않 습 니 다.
void addToTail(Node **ppListNode, int value)
{
Node *pNew = (Node *)malloc(sizeof(Node));
pNew->value = value;
pNew->pnext = NULL;
if (NULL == *ppListNode) // , ,
{
*ppListNode = pNew;
return;
}
else
{
Node *pNode = *ppListNode;
while (pNode->pnext != NULL)
pNode = pNode->pnext;
pNode->pnext = pNew;
}
return;
}
4. 지정 한 위치 에 요소 삽입
이상 상황:
1) 링크 가 비어 있 음
2) 삽입 위치 0
3) 삽입 위치 가 링크 길이 보다 크다
/* pos value*/
void insertNode(Node **ppListNode, int pos, int value)
{
if ((NULL == ppListNode) || (pos < 0))
return;
if (NULL == *ppListNode) // ,
createList(ppListNode, value);
Node *pNode, *pNew;
pNode = *ppListNode;
pNew = (Node *)malloc(sizeof(Node));
pNew->value = value;
pNew->pnext = NULL;
/* 0 , */
if (0 == pos)
{
pNew->pnext = pNode;
*ppListNode = pNew;
return;
}
/* pos pNode*/
while (--pos)
{
pNode = pNode->pnext;
if (NULL == pNode)
return; // ,
}
pNew->pnext = pNode->pnext;
pNode->pnext = pNew;
return;
}
5. 단일 지정 요소 삭제
이상 상황:
1) 링크 가 비어 있 음
2) 삭제 할 요 소 를 헤드 노드 요소 로 한다.
3) 요소 가 링크 에 존재 하지 않 음
지적 해 야 할 것 은 단 방향 링크 에 대해 특정한 노드 를 삭제 할 때 가장 편리 한 방법 은 이 노드 의 앞 노드 를 먼저 찾 는 것 이다. 그러면 이상 한 상황 이 있다. 즉, 앞의 노드 는 링크 의 끝 노드 이 고 링크 는 지정 되 지 않 은 삭제 노드 만 있다 는 것 이다.
/* */
void deleteValue(Node **ppListNode, int value)
{
Node *pNode;
if ((NULL == ppListNode) || (NULL == *ppListNode))
return;
if ((*ppListNode)->value == value) //
{
pNode = *ppListNode;
*ppListNode = pNode->pnext;
free(pNode);
return;
}
pNode = *ppListNode;
/* , while */
if (NULL == pNode->pnext)
return;
/* pNode*/
while (pNode->pnext->value != value)
{
pNode = pNode->pnext;
if (NULL == pNode->pnext)
return; // ,
}
Node *pDel = pNode->pnext; //pNode
pNode->pnext = pDel->pnext;
free(pDel);
return;
}
6. 링크 의 모든 지정 요소 삭제
위의 5 는 링크 에 나타 난 첫 번 째 지정 요소 노드 만 삭제 할 뿐 링크 에 있 는 모든 지정 요소 노드 를 추가 로 삭제 하고 프로그램 은 그다지 수정 되 지 않 았 습 니 다.1 차 삭제 요 소 는 5 시 에 열 거 된 이상 상황 을 다시 고려 해 야 하기 때문에 재 귀적 으로 처리 합 니 다. 그 종료 조건 은 링크 가 비어 있 거나 링크 가 끝 나 는 것 입 니 다.
/* */
void deleteAllValue(Node **ppListNode, int value)
{
Node *pNode;
if ((NULL == ppListNode) || (NULL == *ppListNode))
return;
if ((*ppListNode)->value == value) //
{
pNode = *ppListNode;
*ppListNode = pNode->pnext;
free(pNode);
return deleteAllValue(ppListNode, value);
}
pNode = *ppListNode;
/* , while */
if (NULL == pNode->pnext)
return;
/* pNode*/
while (pNode->pnext->value != value)
{
pNode = pNode->pnext;
if (NULL == pNode->pnext)
return; // ,
}
Node *pDel = pNode->pnext; //pNode
pNode->pnext = pDel->pnext;
free(pDel);
return deleteAllValue(ppListNode, value);
}
다음 테스트 상황 통과:1) 링크 가 비어 있 음
2) 링크 는 하나의 노드 만 있 고 이 노드 는 삭제 대상 노드 와 비 삭제 노드 이다.
3) 링크 에 지정 한 요소 없 음
4) 링크 의 모든 노드 는 삭제 요소 노드 를 지정 합 니 다.
7. 지정 한 위치의 노드 삭제
이상 상황:
1) 링크 가 비어 있 음
2) 삭제 위 치 는 헤드 노드 위치
3) 삭제 위치 가 링크 길이 보다 크다 (링크 끝 노드 뒤에 있 는 노드 포함)
/* pos */
void deleteNode(Node **ppListNode, int pos)
{
if ((NULL == ppListNode) || (NULL == *ppListNode) || (pos < 0))
return;
Node *pNode = *ppListNode;
if (0 == pos) //
{
*ppListNode = pNode->pnext;
free(pNode);
return;
}
/* pos-1 */
while (--pos)
{
pNode = pNode->pnext;
if (NULL == pNode)
return; //
}
Node *pDel = pNode->pnext;
if (NULL == pDel) //
return;
pNode->pnext = pDel->pnext;
free(pDel);
return;
}
8. 순서 인쇄 링크
/* */
void printNode(Node *pListNode)
{
if (pListNode)
{
printf("%d
", pListNode->value);
printNode(pListNode->pnext);
}
}
9. 역순 인쇄 링크
/* */
void printNodeReverse(Node *pListNode)
{
if (pListNode)
{
printNodeReverse(pListNode->pnext);
printf("%d
", pListNode->value);
}
}
10. 링크 노드 개 수 를 되 돌려 줍 니 다.
int countNode(Node *pListNode)
{
/*if (NULL == pListNode)
return 0;
return 1 + countNode(pListNode->pnext);*/
int count = 0;
while (pListNode)
{
pListNode = pListNode->pnext;
++count;
}
return count;
}
마지막 으로 몇 마디 수 다 를 떨 었 다. 실제 응용 할 때 당신 이 따로 링크 를 쓸 필요 가 없다. 다른 사람 이 바퀴 (STL, Linux 및 기타) 를 만 들 었 다. 우 리 는 사용 만 하면 된다. 가장 전형 적 인 바퀴 는 당연히 Linux 커 널 소스 코드 에서 링크 의 수량 구조 로 간단 하면 서도 간단 하지 않다.그러나 우 리 는 이 바퀴 가 어떻게 돌아 가 는 지 알 아야 만 이 바퀴 들 을 더욱 잘 다 룰 수 있다.
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
하나의 단일 체인 테이블의 순환과 귀속 실현을 반전시키다텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.