数据结构 --- 单链表试题
求单链表中有效节点的个数 查找单链表中倒数第k个节点 单链表的反转 单链表的逆序打印
package linkedlist;
import java.util.Stack;
public class SingleLinkedListDemo1 {
public static void main(String[] args) {
Node a = new Node(1);
Node b = new Node(2);
Node c = new Node(3);
Node d = new Node(4);
SingleLinkedList1 singleLinkedList1 = new SingleLinkedList1();
singleLinkedList1.add(a);
singleLinkedList1.add(b);
singleLinkedList1.add(c);
singleLinkedList1.add(d);
singleLinkedList1.list();
System.out.println(SingleLinkedList1.getLength(singleLinkedList1.getHead()));
//是否得到了倒数第k个节点
Node res = SingleLinkedList1.findLastIndexNode(singleLinkedList1.getHead(),2);
System.out.println("res+"+res);
System.out.println("反转单链表:");
SingleLinkedList1.reversetList(singleLinkedList1.getHead());
singleLinkedList1.list();
System.out.println("测试逆序打印单链表:");
SingleLinkedList1.reversePrint(singleLinkedList1.getHead());
}
}
class Node{
public int no;
public Node next;
public Node(int no) {
this.no = no;
}
public Node() {
}
public int getNo() {
return no;
}
public void setNo(int no) {
this.no = no;
}
public Node getNext() {
return next;
}
public void setNext(Node next) {
this.next = next;
}
@Override
public String toString() {
return "node{" +
"no=" + no +
'}';
}
}
class SingleLinkedList1{
private Node head = new Node(0);
//返回head头节点
public Node getHead() {
return head;
}
//显示链表 遍历
public void list(){
//先遍历链表 判断是否为空
if (head.next == null){
System.out.println("链表为空!");
return;
}
Node temp = head.next;
while (true){
if (temp == null) break;
System.out.println(temp);
temp = temp.next;
}
}
//方法:获取到单链表的有效节点个数(如果是带头节点的链表,需求不统及头节点)
public static int getLength(Node head){//方便其他方法调用
if (head.next == null) return 0;
int length = 0;
//定义一个辅助变量
Node cur = head.next;
while (cur != null){
length++;
cur = cur.next;
}
return length;
}
public void add(Node node){
Node temp = head;
while(true){
if(temp.next == null) break;
temp = temp.next;
}
temp.next = node;
}
//查找单链表中的倒数第k个节点
/*思路
* ①编写一个方法接收head节点,同时接收一个index
* ②index是倒数的第index节点
* ③先把链表从头到尾遍历 得到链表的总长度getLength
* ④得到size后,从链表的第一个开始遍历(size-index)个得到
*/
public static Node findLastIndexNode(Node head,int index){
//判断如果链表为空,返回null
if (head.next == null){
return null;//没有找到
}
//第一个遍历得到的链表长度(节点个数)
int size = SingleLinkedList1.getLength(head);
//第二次遍历 size - index的位置,就是我们倒数的第k个节点
if (index <= 0||index>size){
return null;
}
Node cur = head.next;
for (int i =0;i<size-index;i++){
cur = cur.next;
}
return cur;
}
//将单链表反转
public static void reversetList(Node head){
//如果当前链表为空或只有一个节点直接返回
if (head.next ==null ||head.next.next==null)return;
//定义一个辅助的指针,帮我们遍历原来的节点
Node cur = head.next;
Node next = null;//指向当前节点[cur]的下一个节点
Node reverseHead = new Node(0);
//遍历原来的链表,每遍历一个节点就取出 放在新的链表reverseHead的最前端
while (cur != null){
next = cur.next;//暂时保存当前节点的下一个节点
cur.next = reverseHead.next;//将cur的下一个节点指向新的链表最前端
reverseHead.next = cur;//将cur连接到新的链表
cur = next;//下一个节点
}
//将head.next 指向reverseHead.next,实现单链表的反转
head.next = reverseHead.next;
}
//利用栈这个数据结构,将各个节点压入栈中,然后利用栈的先进后出的特点,就实现了逆序打印的效果
//不能先逆转单链表 然后打印 这样会破坏单链表的结构
public static void reversePrint(Node head){
if (head.next == null) return;//空链表不能打印
//创建一个栈,将各个节点压入栈
Stack stack = new Stack<Node>();
Node cur = head.next;
while(cur!=null){
stack.push(cur);
cur = cur.next;//cur后移 这样就可以插入下一个节点
}
//将栈中的节点进行打印,pop出栈
while (stack.size()>0){
System.out.println(stack.pop());//先进后出
}
}
}