在一个int数组里查找这样的数,它大于等于左侧所有数,小于等于右侧所有数。

题目的意思很简单,比如说有数组[1,6,9,2,1,5,15,20],那么满足上述条件的元素为1,15,20。


暴力的方法就是从左到右进行遍历,到达某个数字后,在从0开始遍历到当前下标,找出最大的,再从当前下标遍历到尾,找出最小的,然后根据题意比较一下,这个算法为O(n^2)。

比较简单的算法就是利用一下额外的空间,保存一下,每个元素右侧的最小值,或者左侧的最大值,在反向遍历一次。举个例子。

就如[1,6,9,2,1,5,15,20],如果我们要找到该数组右侧的最小值,则从后向前遍历,20开始,20的右侧的最小值为20,之后15,15右侧的最小值为15,之后5,最小值为5,之后1,最小值为1,那么新的数组就是[1,1,1,1,1,5,15,20]。

之后我们再从左向右遍历数组,并保存当前的最大值,到1,最大值为1,看新的数组,右侧的最小值为1,那么1>=1,1<=1,满足,输出,对于6,更新最大值为6,看新数组6右边的最小值为1,6>=6,但是>1,也就是比右侧最小的值大,不满足条件,不输出。同理遍历一遍就好。

代码如下:

#include <iostream>
#include <assert.h>
using namespace std;

void FindValue(int a[], int size)
{    
    assert(a!=NULL);
    assert(size!=0);

    // 定义一个辅助数组
    int* b = new int[size];
    int min=a[size-1];
    for(int i=size-1; i>=0 ; i--)
    {
        if(a[i]<=min)
        {
            min = a[i];
        }
        b[i] = min;
    }
    
    int max = a[0];
    for(int i=0; i<size; i++)
    {
        if(max <= a[i])
            max = a[i];
        if(a[i]>=max && a[i]<= b[i])
            cout<<a[i]<<endl;
    }

    
    delete[] b;

}


int main()
{
    int a[]={1,6,9,2,1,5,15,20};
    int size = sizeof(a)/sizeof(a[0]);
    for (int i=0; i<size; i++)
    {
        cout<<a[i]<<" ";
    }
    cout<<"\n满足要求的元素为:\n";
    FindValue(a,size);


}
原文地址:https://www.cnblogs.com/cyttina/p/2743067.html