Algorithm || Divide and conquer【Find the median of two equal-length ordered sequences】#03

finds the median of two ordered sequences of equal length

【Problem Description】

For an ordered sequence of length n (assumed to be ascending sequence ) a[0...n-1], the element in the middle is called the median of a. Design an algorithm to find the median of two given ordered sequences.

For example, if the sequence a=(11, 13, 15, 17, 19), the median is 15,
and if b=(2, 4, 6, 8, 20), the median is 6. The median of two ordered sequences of equal length is the median of the ordered sequences containing all their elements. For example, the median of the two ordered sequences a and b is 11. a=(11,13,15,17,19) b=(2,4,6,8,20)

c=(2,4,6,8,11,12,15,17,19,20)

【Algorithm Explanation】

For an ordered sequence a[s...t] containing n elements, when n is an odd number, the median appears at m=(s+t)/2; when n is an even number, the median subscript There are m=(s+t)/2 (lower median) and m=(s+t)/2+1 (upper median). For simplicity, only consider where the median is m=(s+t)/2.
insert image description here
Solve using the dichotomy method.
Find the median a[m1], b[m2] of a and b respectively:
Situation 1 : If a[m1]=b[m2], then a[m1] or b[m2] is the desired median number, the algorithm ends.
Case 2 : If a[m1]<b[m2], discard the first half (the smaller half) of the sequence a, and discard the second half (the larger half) of the sequence b at the same time, requiring that the discarded lengths be equal.
Case 3 : If a[m1]>b[m2], discard the second half (larger half) of sequence a, and discard the first half (smaller half) of sequence b at the same time, requiring the discarded lengths to be equal.

【Complete code】

VS2017 C++

#include<iostream>
using namespace std;
#define MAXN 15

//取a[s..t]序列的前半个子序列
void prepart(int& s, int& t)
{
    
    
	int m = (s + t) / 2;
	t = m;
}
//取a[s..t]序列的后半个子序列
void backpart(int& s, int& t)
{
    
    
	int m = (s + t) / 2;
	//序列中有奇数个元素
	if ((s + t) % 2 == 0)
		s = m;
	//序列中有偶数个元素
	else
		s = m + 1;
}
//求中位数
int midnum(int a[], int s1, int t1, int b[], int s2, int t2)
{
    
    
	int m1, m2;
	if (s1 == t1 && s2 == t2)
		return a[s1] < b[s2] ? a[s1] : b[s2];
	else
	{
    
    
		m1 = (s1 + t1) / 2;//序列1的中位数
		m2 = (s2 + t2) / 2;//序列2的中位数
		if (a[m1] == b[m2])
			return a[m1];//若两个中位数相等则返回该中位数
		else if (a[m1] < b[m2])
		{
    
    
			backpart(s1, t1);//序列1取后半部分
			prepart(s2, t2);//序列2取前半部分
			return midnum(a, s1, t1, b, s2, t2);
		}
		else
		{
    
    
			backpart(s2, t2);//序列2取后半部分
			prepart(s1, t1);//序列1取前半部分
			return midnum(a, s1, t1, b, s2, t2);
		}
	}
}
int main()
{
    
    
	int n;
	int a[MAXN], b[MAXN];
	cout << "请输入数组的大小:";
	cin >> n;
	cout << "请依次输入数组1数据:";
	for (int i = 0; i < n; i++)
		cin >> a[i];
	cout << "请依次输入数组2数据:";
	for (int i = 0; i < n; i++)
		cin >> b[i];
	cout << "中位数是:" << midnum(a, 0, n-1, b, 0, n-1) << endl;
	system("pause");
	return 0;
}

【operation result】

insert image description here

Guess you like

Origin blog.csdn.net/qq_43759081/article/details/121889412