教育行業(yè)A股IPO第一股(股票代碼 003032)

全國(guó)咨詢/投訴熱線:400-618-4000

java數(shù)據(jù)結(jié)構(gòu)-單鏈表的數(shù)據(jù)操作及特性

更新時(shí)間:2018年12月07日11時(shí)28分 來源:傳智播客 瀏覽次數(shù):

# 數(shù)據(jù)結(jié)構(gòu)-單鏈表的數(shù)據(jù)操作及特性

數(shù)據(jù)結(jié)構(gòu)-單鏈表的數(shù)據(jù)操作及特性

## 概述

? 上一章中,我們已經(jīng)入門了單鏈表的添加數(shù)據(jù)以及查詢數(shù)據(jù)打印了,那么當(dāng)我們存儲(chǔ)了數(shù)據(jù),要?jiǎng)h除的時(shí)候怎么辦呢?這章,我們來看看如何刪除數(shù)據(jù)。

![](image\image1.png)

## 根據(jù)數(shù)據(jù)刪除節(jié)點(diǎn)

### 分析

? 根據(jù)數(shù)據(jù)刪除節(jié)點(diǎn),

1. 首先:刪除數(shù)據(jù)分三種情況,1.刪除的節(jié)點(diǎn)是頭節(jié)點(diǎn) 2.刪除的節(jié)點(diǎn)為尾節(jié)點(diǎn) 3.刪除的節(jié)點(diǎn)是中間節(jié)點(diǎn)

2. 其次:需要獲取要?jiǎng)h除的數(shù)據(jù)所對(duì)應(yīng)的節(jié)點(diǎn)以及他的前一個(gè)節(jié)點(diǎn)

3. 刪除節(jié)點(diǎn),需要將鏈表的長(zhǎng)度扣減增加節(jié)點(diǎn)需要長(zhǎng)度增加。

### 實(shí)現(xiàn)

#### 修改增加方法,增加長(zhǎng)度屬性

```java

private transient int size = 0;// 單列表的長(zhǎng)度

/**

* 從尾部添加一個(gè)節(jié)點(diǎn)

*

* @param data

* 要添加的節(jié)點(diǎn)的數(shù)據(jù)

*/

public void add(Object data) {

// 1.構(gòu)建一個(gè)節(jié)點(diǎn)對(duì)象

Node node = new Node(data);

if (head == null) {

// 2.判斷鏈表中是否為空 如果為空 則新增的節(jié)點(diǎn)變成頭節(jié)點(diǎn)

head = node;

} else {

// 3.如果鏈表不為空,則需要查詢到尾部節(jié)點(diǎn)

Node rear = findRearNode();

// 4.向尾部節(jié)點(diǎn)添加一個(gè)節(jié)點(diǎn)

rear.next = node;// rear肯定不為空

}

size++;

}

// 獲取鏈表的長(zhǎng)度

public int size() {

return size;

}

```

#### 編寫刪除的代碼

```java

// 刪除鏈表中的數(shù)據(jù)

public void removeObject(Object data) {

// 賦值為臨時(shí)對(duì)象

Node temp = head;

//記錄要?jiǎng)h除的節(jié)點(diǎn)的前一個(gè)節(jié)點(diǎn)

Node prev = temp;

if (data != null)

while (temp != null) {

if (data.equals(temp.data) && temp.data.hashCode()==data.hashCode()) {

//如果刪除的是頭節(jié)點(diǎn)

if(temp==head){

head=temp.next;//

//如果刪除的是尾部節(jié)點(diǎn)

}else if(temp.next==null){

prev.next=null;

//如果刪除的是中間節(jié)點(diǎn)

}else{

prev.next=temp.next;

}

size--;

break;

}

prev=temp;

//循環(huán)遍歷

temp=temp.next;

}

}

```

代碼解釋:先查詢數(shù)據(jù)在鏈表中是否有,需要循環(huán)遍歷,當(dāng)數(shù)據(jù)一致 并且hashcode一致時(shí),我們才認(rèn)為這才是兩個(gè)相等的數(shù)據(jù)對(duì)象;接著 獲取前一個(gè)節(jié)點(diǎn)對(duì)象。

## 根據(jù)索引刪除節(jié)點(diǎn)

### 分析

? 根據(jù)索引刪除節(jié)點(diǎn),也就是說從第幾個(gè)位置開始刪除,默認(rèn)第一個(gè)位置索引為0 以此類推。

1. 首先:刪除的節(jié)點(diǎn)的索引不能超過總長(zhǎng)度

2. 其次:刪除的節(jié)點(diǎn) 要先找到對(duì)應(yīng)節(jié)點(diǎn)數(shù)據(jù) 再刪除。

### 實(shí)現(xiàn)

?

```java

/**

* 根據(jù)指定的索引來刪除鏈表中的數(shù)據(jù)

* @param index

*/

public void removeIndexObject(int index) {

int count=0;

if(index<0 ||index >=size){

System.out.println("越界");

return;

}

Node temp = head;

//記錄前一個(gè)節(jié)點(diǎn)

Node prev = temp;

while (temp != null) {

if(count==index){

if(index==0){//說明刪除的是頭節(jié)點(diǎn)

head = temp.next;

}else{

//將要?jiǎng)h除的前一個(gè)節(jié)點(diǎn)指向 要?jiǎng)h除節(jié)點(diǎn)的后一個(gè)節(jié)點(diǎn)

prev.next=temp.next;

}

size--;//長(zhǎng)度-1

break;

}

prev=temp;//記錄上一個(gè)節(jié)點(diǎn)

temp=temp.next;

count++;

}

}

```

## 測(cè)試

```java

public static void main(String[] args) {

SingleLink singleLink = new SingleLink();

singleLink.add(1);

singleLink.add(2);

singleLink.add(3);

System.out.println("刪除前=================="+singleLink);

singleLink.removeObject(2);

System.out.println("刪除后=================="+singleLink);

}

```

測(cè)試效果:

```java

刪除前==================[1,2,3]

刪除后==================[1,3]

```

## 總結(jié)

? 通過刪除節(jié)點(diǎn)我們發(fā)現(xiàn),單鏈表的操作刪除時(shí),需要獲取被刪除的節(jié)點(diǎn)的上一個(gè)節(jié)點(diǎn),獲取上一個(gè)節(jié)點(diǎn)相對(duì)來時(shí)比較麻煩。如果使用雙鏈表,那么這個(gè)問題就解決了。而且效率要比單鏈表要高些。下一章,我們來學(xué)習(xí)下雙鏈表相關(guān)的知識(shí),看是如何添加和刪除數(shù)據(jù)的。

0 分享到:
和我們?cè)诰€交談!