复杂度 常数操作 在算法分析中,”常数操作”(constant-time operation)指的是执行时间不随输入规模变化的操作,其时间复杂度为 O (1)。以下是关于复杂度和常数操作的详细说明:
常数操作的定义
特点 :执行时间固定,与输入数据量无关。
示例 :
基本算术运算(如 a + b、x * y)。
数组通过索引访问(如 arr[i])。
指针解引用或赋值(如 p = q)。
简单的比较(如 if (x < y))。
哈希表的插入、查找(假设哈希冲突极少)。
复杂度分析中的常数操作
大 O记号 :忽略常数项和低阶项,但实际编程中常数因子可能影响性能。
例如,两个算法均为 O (n ),但一个的常数操作更少,可能更快。
示例对比 :
算法 A :每次循环执行 2 次常数操作 → 2n 次操作 → O (n )。
算法 B :每次循环执行 5 次常数操作 → 5n 次操作 → 仍为 O (n ),但实际更慢。
选择,冒泡,插入都是O (n * n )的时间复杂度,其中插入排序的最好时间复杂度是O (n ),最差的O (n * n )。
对数器 对数器(对数器测试法)是一种用于验证算法正确性的测试方法,通常用于对比待测算法与暴力解法(或已知正确算法) ,通过随机生成大量测试数据 来检查两者结果是否一致。它广泛应用于算法竞赛、面试准备和工程开发中,尤其适用于难以直接证明正确性的算法 。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 class Program { static void Main (string [] args ) { int testTimes = 100000 ; int maxSize = 100 ; int maxValue = 100 ; bool success = true ; Random rnd = new Random(); for (int i = 0 ; i < testTimes; i++) { int [] arr1 = GenerateRandomArray(maxSize, maxValue); int [] arr2 = CopyArr(arr1); InsertSort1(arr1); InsertSort2(arr2); if (!IsEqual(arr1, arr2)) { success = false ; Console.WriteLine("出错数据:" ); PrintArray(arr1); PrintArray(arr2); break ; } } Console.WriteLine(success ? "测试通过!" : "测试失败!" ); } public static int [] CopyArr (int [] arrs ) { int N = arrs.Length; int [] arrays = new int [N]; if (N == 0 ) { return arrays; } for (int i = 0 ;i< N; i++) { arrays[i] = arrs[i]; } return arrays; } public static int [] generateRandomArray (int maxSize,int maxValue ) { Random rnd = new Random(); int [] arrs = new int [(int )rnd.Next(maxSize) + 1 ]; for (int i = 0 ; i < arrs.Length; i++) { arrs[i] =(int )rnd.Next(maxValue)- (int )rnd.Next(maxValue); } return arrs; } public static void Swap (int [] arr,int i,int j ) { int temp = arr[j]; arr[j] = arr[i]; arr[i] = temp; } public static void InsertSort1 (int [] arrs ) { if (arrs == null || arrs.Length < 2 ) return ; int N = arrs.Length; for (int end = 1 ;end < N; end++) { int newIndex = end; while (newIndex - 1 >=0 && arrs[newIndex - 1 ] > arrs[newIndex]) { Swap(arrs,newIndex-1 ,newIndex); newIndex--; } } } public static void InsertSort2 (int [] arrs ) { if (arrs == null || arrs.Length < 2 ) return ; int N = arrs.Length; for (int end = 1 ; end < N; end++) { for (int pre = end - 1 ;pre >=0 &&arrs[pre]>arrs[pre+1 ];pre--) { Swap(arrs,pre, pre+1 ); } } } public static void PrintArray (int [] arrs ) { for (int i = 0 ; i < arrs.Length; i++) { Console.Write(arrs[i] + " " ); } Console.WriteLine(); } }
二分法 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 public static bool isExist (int [] arrs,int num ) { if (arrs.Length == 0 || arrs == null ) return false ; int R = arrs.Length - 1 ; int L = 0 ; int mid = 0 ; while (L <= R) { mid = L + ((R - L) >> 1 ); if (arrs[mid] == num) return true ; else if (arrs[mid] < num) L = mid + 1 ; else R = mid -1 ; } return false ; } public static int nearestIndex (int [] arrs,int num ){ int R = arrs.Length - 1 ; int L = 0 ; int index = -1 ; while (L <= R) { int mid = L + ((R - L) << 1 ); if (arrs[mid] >= num) { index = mid; R = mid -1 ; } else L = mid +1 ; } return index; }