Problem:

There are many unordered numbers, from which we can find the maximum number of K. Assume they are not equal.

Solution 1:

If there are not many pieces of data, for example, a few thousands or so, we can sort the order to find the maximum K number. You can select quick or heap sorting for sorting.

# Include <stdio. h> # include <stdlib. h> int CMP (const void * a, const void * B) {return * (int *) A-* (int *) B;} int main () {int N, k; int num [1000]; while (scanf ("% d", & N, & K )! = EOF) {// input data for (INT I = 0; I <n; I ++) {scanf ("% d", & num [I]);} // sort qsort (Num, N, sizeof (Num [0]), CMP); // select the maximum K number for (I = n-k; I <N; I ++) {printf ("% d", num [I]);} printf ("\ n");} return 0 ;}

Solution 2:

We can continue to optimize the above algorithm, we just select the largest K number from these unordered numbers, do not need the first k Data Order, also do not need the N-K Data Order.

How can we avoid the order of the N-K after?

Recall that each step in the quick sorting is to divide the data to be sorted into two groups. One group of data has a larger number than the other, then perform similar operations on the two groups respectively.

And then proceed ...... In this problem, assuming n numbers are stored in array S, we randomly find an element x from array S and divide the array into two parts: SA and Sb.

The element in SA is greater than or equal to X, and the element in Sb is less than X. There are two possibilities:

1. the number of elements in SA is less than K. The number in SA and the maximum K-in SB | sa | elements (| sa | the number of elements in SA) is the maximum K number in array S.

2. If the number of elements in SA is greater than or equal to K, the maximum K Elements in SA must be returned.

In this way, the problem is continuously decomposed into smaller problems, and the average time complexity is O (n * log2k ).

# Include <stdio. h> # include <stdlib. h> // perform a quick sorting. Use the number of Enis to split the int partition (int A [], int low, int high) {int I, j, index; I = low; j = high; // sentinel Index = A [I]; while (I <j) {// enter a [I] While (A [J] <index & I <j) {J --;} from the right to the left --;} // assign a value greater than the index value to a [I] if (I <j) {A [I] = A [J]; I ++ ;} // enter a [J] While (A [I] >=index & I <j) {I ++;} from the left to the right ;} // assign the number of values smaller than the index value to a [J] if (I <j) {A [J] = A [I]; j --;}} A [I] = index; return I;} int kbig (int A [], int low, int high, int K) {int index, N; If (low
Solution 3: (this method is better)

Use the minimum heap with a capacity of K to store the maximum number of K. The minimum heap top element is the smallest of the maximum K numbers. Each time a data X is scanned, if X is smaller than Y on the top of the heap, the original heap does not need to be changed because this element is smaller than the maximum K number. If X is larger than the heap top element, use X to replace heap top element Y. After replacement, X may damage the structure of the smallest heap. You need to adjust the heap to maintain the heap nature. Adjust the time complexity of the process to O (logk ).

When the data volume is large (10 billion? At this time, the data cannot be fully loaded into the memory, so it is required to traverse the array as little as possible) This method can be used.

# Include <stdio. h> # include <stdlib. h> // adjust the subtree with index as the root // K: number of elements in the heap int minheap (int A [], int index, int K) {int minindex = index; // The left subnode int leftindex = 2 * index; // The right subnode int rightindex = 2 * index + 1; if (leftindex <= K & A [leftindex] <A [minindex]) {minindex = leftindex ;} if (rightindex <= K & A [rightindex] <A [minindex]) {minindex = rightindex;} // If a [Index] is the smallest, the subtree rooted in index is already the smallest heap. Otherwise, the subnode of index has the smallest element. // The A [Index], a [minindex] is exchanged. So that the index and children can satisfy the heap int temp; If (minindex! = Index) {// exchange a [Index], a [minindex] temp = A [Index]; A [Index] = A [minindex]; A [minindex] = temp; // re-adjust the minheap (A, minindex, k);} return 0;} // heap: convert an array a [1-K] into a minimum heap int buildminheap (int A [], int K) {int I; // use the minimum heap with a capacity of K to store the maximum K number for (I = K; I> = 1; I --) {// adjust the tree with I as the root node to make it the smallest heap minheap (A, I, K);} return 0 ;}int main () {int n = 6; int K = 3; // A [0] is not required. The heap root node is int A [] = {0, 3, 17,8, 27,7, 20} starting from 1 }; // bucket maxheap constructs a minimum heap buildminheap (A, K) using the input array; // The minimum element in the array is in the root a [1] For (INT I = N; I> K; I --) {// If X is smaller than Y, the original heap does not need to be changed. // If X is larger than y, then replace heap top element y with X. After replacement, X may damage the structure of the minimum heap. You need to adjust the heap to maintain the heap's int temp; if (A [1] <A [I]) {// exchange temp = A [I]; A [I] = A [1]; A [1] = temp; // re-adjust to keep the minimum heap properties minheap (A, 1, k) ;}}for (I = 1; I <= K; I ++) {printf ("% d", a [I]);} return 0 ;}

If you do not understand the heap usage, refer to heap sorting.

In heap sorting, the maximum heap and the minimum heap are almost the same. You can see it by yourself.

Solution 4:

This method is limited.

If all N numbers are positive integers and the value range is not large. You can apply for a space, record the number of occurrences of each integer, and then obtain the maximum number of K values from large to small.

# Include <stdio. h> # include <string. h> const int maxn = 100; int count [maxn]; int main () {int K = 3; int A [] = }; memset (count, 0, maxn); // count the number of duplicates for (INT I = 0; I <6; I ++) {count [A [I] ++;} // select the maximum K count int sumcount = 0; for (I = maxn; I> = 0; I --) {sumcount + = count [I]; If (sumcount> = k) {break ;}// output int Index = I; for (I = index; I <maxn; I ++) {If (count [I]> 0) {printf ("% d", I) ;}} printf ("\ n"); Return 0 ;}