Java 实现有序链表

有序链表:

按关键值排序。

删除链头时,就删除最小(/最大)的值,插入时,搜索插入的位置。

插入时须要比較O(N),平均O(N/2),删除最小(/最大)的在链头的数据时效率为O(1),

假设一个应用须要频繁的存取(插入/查找/删除)最小(/最大)的数据项,那么有序链表是一个不错的选择

优先级队列 能够使用有序链表来实现

有序链表的插入排序:

对一个无序数组,用有序链表来排序,比較的时间级还是O(N^2)

复制时间级为O(2*N),由于复制的次数较少,第一次放进链表数据移动N次,再从链表拷贝到数组,又是N次

每插入一个新的链结点,不须要复制移动数据。仅仅须要改变一两个链结点的链域

import java.util.Arrays;
import java.util.Random;

/**
 * 有序链表 对数组进行插入排序
 * @author stone
 */
public class LinkedListInsertSort<T extends Comparable<T>> {

	private Link<T> first;		//首结点
	public LinkedListInsertSort() {

	}

	public boolean isEmpty() {
		return first == null;
	}

	public void sortList(T[] ary) {
		if (ary == null) {
			return;
		}
		//将数组元素插入进链表,以有序链表进行排序
		for (T data : ary) {
			insert(data);
		}
		//

	}

	public void insert(T data) {// 插入 到 链头, 以从小到大排序
		Link<T> newLink = new Link<T>(data);
		Link<T> current = first, previous = null;
		while (current != null && data.compareTo(current.data) > 0) {
			previous = current;
			current = current.next;
		}
		if (previous == null) {
			first = newLink;
		} else {
			previous.next = newLink;
		}
		newLink.next = current;
	}

	public Link<T>  deleteFirst() {//删除 链头
		Link<T> temp = first;
		first = first.next; //变更首结点,为下一结点
		return temp;
	}

	public Link<T> find(T t) {
		Link<T> find = first;
		while (find != null) {
			if (!find.data.equals(t)) {
				find = find.next;
			} else {
				break;
			}
		}
		return find;
 	}

	public Link<T> delete(T t) {
		if (isEmpty()) {
			return null;
		} else {
			if (first.data.equals(t)) {
				Link<T> temp = first;
				first = first.next; //变更首结点,为下一结点
				return temp;
			}
		}
		Link<T> p = first;
		Link<T> q = first;
		while (!p.data.equals(t)) {
			if (p.next == null) {//表示到链尾还没找到
				return null;
			} else {
				q = p;
				p = p.next;
			}
		}

		q.next = p.next;
		return p;
	}

	public void displayList() {//遍历
		System.out.println("List (first-->last):");
		Link<T> current = first;
		while (current != null) {
			current.displayLink();
			current = current.next;
		}
	}

	public void displayListReverse() {//反序遍历
		Link<T> p = first, q = first.next, t;
		while (q != null) {//指针反向,遍历的数据顺序向后
			t = q.next; //no3
			if (p == first) {// 当为原来的头时,头的.next应该置空
				p.next = null;
			}
			q.next = p;// no3 -> no1  pointer reverse
			p = q; //start is reverse
			q = t; //no3 start
		}
		//上面循环中的if里。把first.next 置空了, 而当q为null不运行循环时,p就为原来的最且一个数据项,反转后把p赋给first
		first = p;
		displayList();
	}

	class Link<T> {//链结点
		T data;		//数据域
		Link<T> next; //后继指针,结点		链域
		Link(T data) {
			this.data = data;
		}
		void displayLink() {
			System.out.println("the data is " + data.toString());
		}
	}

	public static void main(String[] args) {
		LinkedListInsertSort<Integer> list = new LinkedListInsertSort<Integer>();
		Random random = new Random();
		int len = 5;
		Integer[] ary = new Integer[len];
		for (int i = 0; i < len; i++) {
			ary[i] = random.nextInt(1000);
		}
		System.out.println("----排序前----");
		System.out.println(Arrays.toString(ary));
		System.out.println("----链表排序后----");
		list.sortList(ary);
		list.displayList();
	}
}

打印

----排序前----
[595, 725, 310, 702, 444]
----链表排序后----
List (first-->last):
the data is 310
the data is 444
the data is 595
the data is 702
the data is 725
时间: 2024-11-07 16:19:07

Java 实现有序链表的相关文章

21. Merge Two Sorted Lists (Java 合并有序链表 空间复杂度O(1))

题目: Merge two sorted linked lists and return it as a new list. The new list should be made by splicing together the nodes of the first two lists. 分析:合并两个有序序列,这个归并排序中的一个关键步骤.这里是要合并两个有序的单链表.由于链表的特殊性,在合并时只需要常量的空间复杂度. 编码: public ListNode mergeTwoLists(Li

Java单链表、双端链表、有序链表实现

Java单链表.双端链表.有序链表实现 原创 2014年03月31日 23:45:35 标签: Java / 单链表 / 双端链表 / 有序链表 65040 单链表: insertFirst:在表头插入一个新的链接点,时间复杂度为O(1) deleteFirst:删除表头的链接点,时间复杂度为O(1) 有了这两个方法,就可以用单链表来实现一个栈了,见http://blog.csdn.net/a19881029/article/details/22579759 find:查找包含指定关键字的链接点

leetcode合并两个有序链表Java实现

将两个有序链表合并为一个新的有序链表并返回.新链表是通过拼接给定的两个链表的所有节点组成的. 示例: 输入:1->2->4, 1->3->4 输出:1->1->2->3->4->4 两个有序链表的排序,实际上可以看成一个单链表使用归并排序的最后一个环节:“将两个排好序的子序列合并为一个子序列:每次都是从未比较的两个子序列的最小值中选出一个更小值”. /** * Definition for singly-linked list. * public cl

合并两个有序链表(java实现)

题目: 将两个有序链表合并为一个新的有序链表并返回.新链表是通过拼接给定的两个链表的所有节点组成的. 示例: 输入:1->2->4, 1->3->4 输出:1->1->2->3->4->4看到这个题,让我想起上次写的博客,合并两个有序的数组.这个题,是链表的合并,这就比较好移动,可以用递归实现链表的拼接所以,代码如下: /** * Definition for singly-linked list. * public class ListNode {

LeetCode:Merge Two Sorted Lists - 拼接两个有序链表

1.题目名称 Merge Two Sorted Lists(按升序拼接两个有序链表) 2.题目地址 https://leetcode.com/problems/merge-two-sorted-lists/ 3.题目内容 英文:Merge two sorted linked lists and return it as a new list. The new list should be made by splicing together the nodes of the first two l

算法总结之 打印两个有序链表的公共部分

给定两个有序链表的头指针 head1 和 head2,打印两个链表的公共部分 思路: 有序嘛, 如果head1 的值小于 head2, head1往下移动 如果head2的值小于head1,head2往下移动 如果相等,打印这个值,然后同时向下移动 两个有一个为null, 整个过程停止 package TT; import java.time.temporal.ValueRange; public class Test84 { public class Node{ public int valu

LeetCode-合并两个有序链表

.title { text-align: center; margin-bottom: .2em } .subtitle { text-align: center; font-size: medium; font-weight: bold; margin-top: 0 } .todo { font-family: monospace; color: red } .done { font-family: monospace; color: green } .priority { font-fami

合并N个有序链表与FQ公平调度

下大雨了,于是就想表达一些只有下雨才能表达的东西.夜半酒酣惊觉起,使我流泪忆江南-前天晚上下班带着小小在暴雨中狂奔,非常舒服,其实也算是流言终结者吧.反驳一下几千年来在我国北方通过长辈代代相传的淋雨和感冒之间的因果关系. ??昨天早上很早起来,听雨作文,今天早上继续,文章不算太长. 合并两个有序链表 这是一道超级常见的课后作业题或者面试题,网上答案一搜一箩筐,我自己也写了一个不会编程版: 有序链表合并C语言递归版–我稍微会一点编程:https://blog.csdn.net/dog250/art

LeetCode 21. 合并两个有序链表(Merge Two Sorted Lists)

21. 合并两个有序链表 21. Merge Two Sorted Lists 题目描述 将两个有序链表合并为一个新的有序链表并返回.新链表是通过拼接给定的两个链表的所有节点组成的. LeetCode21. Merge Two Sorted Lists 示例: 输入: 1->2->4, 1->3->4 输出: 1->1->2->3->4->4 Java 实现 ListNode 类 class ListNode { int val; ListNode n