如何在已排序的数组中进行搜索?

在有序数组中,可以使用二分查找的方式进行查找操作。

小白学算法-数据结构和算法教程:在已排序数组中搜索、插入和删除 | 数组运算_ci

JavaScript 代码实现

<script> 
// Javascript 程序实现
// 在排序数组中进行二进制搜索
function binarySearch( arr, low, high, key) 
{ 
	if (high < low) 
		return -1; 
		/*low + (high - low)/2;*/
	let mid = Math.trunc((low + high) / 2); 
	if (key == arr[mid]) 
		return mid; 
	if (key > arr[mid]) 
		return binarySearch(arr, (mid + 1), high, key); 
	return binarySearch(arr, low, (mid - 1), key); 
} 
	
// 让我们在下面的数组中搜索 3
let arr = [ 5, 6, 7, 8, 9, 10 ]; 
let n, key; 

n = arr.length; 
key = 10; 

document.write( "Index: " + binarySearch(arr, 0, n - 1, key) 
               + "</br>"); 
	
	
</script>

输出

指数:5

时间复杂度:O(log(n)) 使用二分查找
辅助空间:由于递归调用,O(log(n)),否则迭代版本使用 O(1) 的辅助空间。

如何插入已排序的数组?

在排序数组中,使用二分搜索对给定元素的可能位置执行搜索操作,然后执行插入操作,然后移动元素。在未排序的数组中,插入操作比排序的数组更快,因为我们不必关心元素放置的位置。

小白学算法-数据结构和算法教程:在已排序数组中搜索、插入和删除 | 数组运算_数组_02

javaScript 代码实现:

<script> 

// JavaScript 程序在排序数组中插入
// 在排序数组中插入一个元素
// 在给定容量的 arr[] 中插入一个键。
// n 是 arr[] 的当前大小。
// 如果插入成功,函数返回 n+1
// 则返回 n+1,否则返回 n。
function insertSorted( arr, n, key, capacity) 
{ 

  // Cannot insert more elements if n is already 
  // more than or equal to capacity 
  if (n >= capacity) 
    return n; 

  var i; 
  for (i = n - 1; (i >= 0 && arr[i] > key); i--) 
    arr[i + 1] = arr[i]; 

  arr[i + 1] = key; 

  return (n + 1); 
} 

var arr = new Array(20); 
arr[0] = 12; 
arr[1] = 16; 
arr[2] = 20; 
arr[3] = 40; 
arr[4] = 50; 
arr[5] = 70; 
var capacity = arr.length; 
var n = 6; 
var key = 26; 

document.write("\nBefore Insertion: "); 
for (var i = 0; i < n; i++) 
  document.write(arr[i] + " "); 

// Inserting key 
n = insertSorted(arr, n, key, capacity); 

document.write("<br>" +"\nAfter Insertion: "); 
for (var i = 0; i < n; i++) 
  document.write(arr[i] + " "); 
			
</script>

输出

插入前:12 16 20 40 50 70
插入后:12 16 20 26 40 50 70

复杂度分析:

时间复杂度: O(N) [在最坏的情况下,可能必须移动所有元素] 
辅助空间: O(1)

如何删除已排序的数组?

在删除操作中,采用二分查找的方式查找要删除的元素,然后通过移位的方式进行删除操作。

小白学算法-数据结构和算法教程:在已排序数组中搜索、插入和删除 | 数组运算_数组_03

javascript 代码实现

<script> 

// JavaScript 程序从排序数组中删除一个
// 从排序数组中删除一个元素

// 二分查找
function binarySearch(arr, low, high, key) 
{ 
  if (high < low) 
    return -1; 
  let mid = (low + high) / 2; 
  if (key == arr[mid]) 
    return mid; 
  if (key > arr[mid]) 
    return binarySearch(arr, (mid + 1), high, key); 
  return binarySearch(arr, low, (mid - 1), key); 
} 

/* 删除元素的函数 */
	function deleteElement( arr, n, key) 
	{ 
// 查找要删除元素的位置
		let pos = binarySearch(arr, 0, n - 1, key); 

		if (pos == -1) { 
			document.write("Element not found"); 
			return n; 
		} 
/* 删除元素的函数 */
		let i; 
		for (i = pos; i < n - 1; i++) 
			arr[i] = arr[i + 1]; 

		return n - 1; 
	} 

	
let i; 
let arr = [ 10, 20, 30, 40, 50 ]; 

let n = arr.length; 
let key = 30; 

document.write("Array before deletion:\n"); 
for (i = 0; i < n; i++) 
  document.write(arr[i] + " "); 

n = deleteElement(arr, n, key); 

document.write("<br>"+"Array after deletion:\n"); 
for (i = 0; i < n; i++) 
  document.write(arr[i] + " "); 

</script>

输出

删除前的数组
10 20 30 40 50 

删除后的数组
10 20 40 50

复杂度分析:

时间复杂度: O(N)。在最坏的情况下,所有元素可能都必须移动
辅助空间: O(log N)。将使用隐式堆栈