用于查找数组中最大和第二大数字的程序

时间:2017-02-22 20:04:51

标签: c arrays data-structures

我在很多网站上搜索过这个问题。他们通过一些不同的方法来做到这一点。 如果我将数组的第一个元素输入为最大,即authHandler,则此代码不提供输出。 我认为需要做一些小改动。 谁能告诉我?

a[0]

17 个答案:

答案 0 :(得分:5)

我将忽略处理输入,只是分散注意力。

简单的方法就是对它进行排序。

#include <stdlib.h>
#include <stdio.h>

int cmp_int( const void *a, const void *b ) {
    return *(int*)a - *(int*)b;
}

int main() {
    int a[] = { 1, 5, 3, 2, 0, 5, 7, 6 };
    const int n = sizeof(a) / sizeof(a[0]);

    qsort(a, n, sizeof(a[0]), cmp_int);
    printf("%d %d\n", a[n-1], a[n-2]);
}

但这并不是效率最高的,因为它是O(n log n),这意味着当数组越大时,比较的数量越快越大。不是太快,比指数慢,但我们可以做得更好。

我们可以在O(n)或“线性时间”执行此操作,这意味着当数组变大时,比较的数量会以相同的速率增长。

循环遍历跟踪最大值的数组,这是查找最大值的常用方法。当您找到新的最大值时,旧的最大值将成为第二高的数字。

不是使用第二个循环来找到第二高的数字,而是输入一个特殊情况,以便进入第二高的数字。

#include <stdio.h>
#include <limits.h>

int main() {
    int a[] = { 1, 5, 3, 2, 0, 5, 7, 6 };
    // This trick to get the size of an array only works on stack allocated arrays.
    const int n = sizeof(a) / sizeof(a[0]);

    // Initialize them to the smallest possible integer.
    // This avoids having to special case the first elements.
    int max = INT_MIN;
    int second_max = INT_MIN;

    for( int i = 0; i < n; i++ ) {
        // Is it the max?
        if( a[i] > max ) {
            // Make the old max the new 2nd max.
            second_max = max;
            // This is the new max.
            max = a[i];
        }
        // It's not the max, is it the 2nd max?
        else if( a[i] > second_max ) {
            second_max = a[i];
        }
    }

    printf("max: %d, second_max: %d\n", max, second_max);
}

可能有一种更优雅的方式,但这最多只能进行2n次比较。充其量它会做n。

请注意,有一个未解决的问题如何处理{ 1, 2, 3, 3 }。应该返回3, 3还是2, 3?我会留给你做出相应的决定和调整。

答案 1 :(得分:1)

如果您需要找到现有数组中最大和第二大的元素,请参阅上面的答案(Schwern的答案包含我将使用的方法)。

然而;需要找到现有阵列中最大和第二大的元素通常表明存在设计缺陷。整个阵列不会神奇地出现 - 它们来自某个地方,这意味着最有效的方法是跟踪当前最大和当前第二大阵列#34;正在创建数组。

例如;对于您的原始代码,数据来自用户;并通过跟踪用户输入的最大和第二大值&#34;在从用户获取值的循环内部,跟踪信息的开销将被等待用户按下键的时间隐藏,您不再需要在用户等待结果时进行搜索,而你根本不需要一个阵列。

它是这样的:

int main() {
    int largest1 = 0, largest2 = 0, i, temp;

    printf("enter number of elements you want in array");
    scanf("%d", &n);
    printf("enter elements");
    for (i = 0; i < n; i++) {
        scanf("%d", &temp);
        if(temp >= largest1) {
            largest2 = largest1;
            largest1 = temp;
        } else if(temp > largest2) {
            largest2 = temp;
        }
    }
    printf("First and second largest number is %d and %d ", largest1, largest2);
}

答案 2 :(得分:0)

问题不明确:如果数组可能包含重复值,您是否应该找到2个最大的不同值或两个最大可能相同的值?

您的代码似乎表明您想要第一种方法,但如果最大值为a[0]则会出现问题。您应该使用额外的布尔值来跟踪您是否找到了不同的值。

您还应测试不同scanf()来电的返回值,并从main()返回0。

以下是修改后的版本:

#include <stdio.h>

int main(void) {
    int a[10], n, i;
    int largest1, largest2, has_largest2;

    printf("enter number of elements you want in array: ");
    if (scanf("%d", &n) != 1)
        return 1;
    if (n < 2) {
        printf("need at least 2 elements\n");
        return 1;
    }
    printf("enter elements: ");
    for (i = 0; i < n; i++) {
        if (scanf("%d", &a[i]) != 1) {
            printf("input error\n");
            return 1;
        }
    }
    largest1 = a[0];
    for (i = 1; i < n; i++) {
        if (a[i] > largest1) {
            largest1 = a[i];
        }
    }
    has_largest2 = largest2 = 0;
    for (i = 0; i < n; i++) {
        if (a[i] < largest1) {
            if (!has_largest2) {
                has_largest2 = 1;
                largest2 = a[i];
            } else
            if (a[i] > largest2) {
                largest2 = a[i];
            }
        }
    }
    if (has_largest2) {
        printf("First and second largest number is %d and %d\n",
               largest1, largest2);
    } else {
        printf("All values are identical to %d\n", largest1);
    }
    return 0;
}

答案 3 :(得分:0)

你可以一次性做到最好。

最大值和最大值2在输入时设置为INT_MIN。 然后逐步完成数组。如果最大值小于数字,则最大值2变为最大值,则最大值变为新数字(或者如果要允许重复,则小于或等于)。如果最大值大于新数字,则测试最大值2。

请注意,此算法可以扩展到查找数组中的前三个或四个,然后再变得过于繁琐,只需排序就可以了。

答案 4 :(得分:0)

尽管可以在一次扫描中完成,但要更正自己的代码,则必须将maximum2声明为int.Min,因为它会阻止large2最初持有最大值。

答案 5 :(得分:0)

您的代码存在问题是一个逻辑问题(大多数编码都是这个问题)。如果最大的数字是第一个那么它得到第二大数字错误......为什么?

那么,看看你决定第二大数字的逻辑。你首先将它设置为等于数组中的第一个元素,然后你通过数组并在元素大于当前第二大数字时更改索引(由于我们已经将它设置为最大的数字!)。

为了解决这个问题你可以这样做:检查最大数字是否是第一个,如果是,那么将它设置为第二个元素(然后特殊情况下有人要求在一个元素中找到最高的两个元素数组,没有读过数组的末尾。)

我认为chqrlie的回答中给出的方法一次性完成这一切是最好的。也是合乎逻辑的:写一个程序来找到最大的数字。第二大数字,那是以前最大的数字!

答案 6 :(得分:0)

//我认为它很简单

#include<stdio.h>
int main()

{
int a1[100],a2[100],i,t,l1,l2,n;
printf("Enter the number of elements:\n");
scanf("%d",&n);
printf("Enter the elements:\n");
for(i=0;i<n;i++)
{
    scanf("%d",&a1[i]);
}
l1=a1[0];
for(i=0;i<n;i++)
{
    if(a1[i]>=l1)
    {
        l1=a1[i];
        t=i;
    }
}
for(i=0;i<(n-1);i++)
{
    if(i==t)
    {
        continue;
    }
    else
    {
        a2[i]=a1[i];
    }
}
l2=a2[0];
for(i=1;i<(n-1);i++)
{
    if(a2[i]>=l2 && a2[i]<l1)
    {
        l2=a2[i];
    }
}
printf("Second highest number is %d",l2);
return 0;
}

答案 7 :(得分:0)

无需使用Third循环来检查数组中的第二大数字。您只能使用两个循环(一个用于插入,另一个用于检查。

参考此代码。

#include <stdio.h>

int main()

{
int a[10], n;

int i;

printf("enter number of elements you want in array");

scanf("%d", &n);

printf("enter elements");

for (i = 0; i < n; i++) {
    scanf("%d", &a[i]);
}

int largest1 = a[0],largest2 = a[0];

for (i = 0; i < n; i++) 
{
    if (a[i] > largest1) 
    {
         largest2=largest1;
         largest1 = a[i];
    }
}

printf("First and second largest number is %d and %d ", largest1, largest2);
}

希望此代码适合您。

享受编码:)

答案 8 :(得分:0)

您需要更好地保留数组成员的索引,因为它们唯一这是一个只有很少更改的工作代码:

#include<stdio.h>
int main()
{
    int a[10],n;
    int largest1,largest2,i;

    printf("enter number of elements you want in array");
    scanf("%d",&n);
    printf("enter elements");
    for(i=0;i<n;i++)
    {
        scanf("%d",&a[i]);
    }
    largest1=0;
    for(i=0;i<n;i++)
    {
        if(a[i]>a[largest1])
        {
            largest1=i;
        }
    }
    if(largest1!=0) // this condition to select another index than the largest
        largest2=0;
    else
        largest2=n-1;
    for(i=0;i<n && i != largest1 ;i++)
    {
        if(a[i]>a[largest2])
            largest2=i;
    }
    printf("First and second largest number is %d and %d ",a[largest1],a[largest2]);
}

请注意,当数组大小为1时,值将相同。

答案 9 :(得分:0)

在不使用任何字符串功能的情况下找到您的第二大号码

int array[];//Input array
int firstLargest, secondLargest;
int minNumber = -1;//whatever smallest you want to add here
/*There should be more than two elements*/
if (array_size < 2)
{
    printf("Array is too small");
    return;
}

firstLargest = secondLargest = minNumber;
for (index = 0; index < array_size ; ++index)
{
    //Largest number check
    if (array[index] > first)
    {
        secondLargest = firstLargest;
        firstLargest = array[index];
    }

    //It may not larger than first but can be larger than second number
    else if (array[index] > secondLargest && array[index] != firstLargest)
{
        secondLargest = array[index];
}

//Finally you got your answer
if (secondLargest == minNumber)
{
    printf("No Second largest number");
}
else
{
    printf("Second Largest Number is %d", secondLargest);
}

答案 10 :(得分:0)

以下是单个for循环的答案。

int array[] = { 10, 15, 13, 20, 21, 8, 6, 7, 9, 21, 23 };
const int count = sizeof(a) / sizeof(a[0]);
int lastMaxNumber = 0;
int maxNumber = 0;

for (int i = 0; i < count; i++) {

    // Current number
    int num = array[i];

    // Find the minimum and maximum from (num, max)
    int maxValue = (num > maxNumber) ? num : maxNumber;
    int minValue = (num < maxNumber) ? num : maxNumber;

    // If minValue is greater than lastMaxNumber, update the lastMaxNumber
    if minValue > lastMaxNumber {
        lastMaxNumber = minValue;
    }

    // Updating maxNumber
    maxNumber = maxValue;
}

printf("%d", lastMaxNumber);

答案 11 :(得分:0)

尝试一下:

    firstMax = arr[0];

    for (int i = 0; i<n; i++) {

        if (firstMax < arr[i]  ) {
            secondMax = firstMax;
            firstMax = arr[i];
        }
    }

答案 12 :(得分:-1)

localhost | FAILED | rc=1 >>
unable to prepare context: unable to evaluate symlinks in Dockerfile path: lstat /home/test/Dockerfile: no such file or directory

答案 13 :(得分:-1)

试试这个:

public static void main(String[] args) throws IndexOutOfBoundsException {

    int[] a = { 12, 19, 10, 3, 9, 8 };
    int n = a.length;
    int larg = a[0];
    int larg2 = a[0];

    for (int i = 0; i < n; i++) {
        if (larg < a[i]) {
            larg = a[i];

        }
        if (a[i] > larg2 && larg < a[i]) {
            larg2 = a[i];

        }
    }

    System.out.println("largest " + larg);
    System.out.println("largest2 " + larg2);

}

答案 14 :(得分:-2)

package secondhighestno;

import java.util.Scanner;

/**
 *
 * @author Laxman
 */
public class SecondHighestno {

    /**
     * @param args the command line arguments
     */
    public static void main(String[] args) {
        // TODO code application logic here
        Scanner sc=new Scanner(System.in);
        int n =sc.nextInt();
        int a[]=new int[n];
        for(int i=0;i<n;i++){
            a[i]=sc.nextInt();
        }
        int max1=a[0],max2=a[0];
        for(int j=0;j<n;j++){
            if(a[j]>max1){
                max1=a[j];
            }
        }
        for(int k=0;k<n;k++){
            if(a[k]>max2 && max1>a[k]){
                max2=a[k];
            }
        }
        System.out.println(max1+" "+max2);
    }
}

答案 15 :(得分:-2)

如果您需要找到数组中最大或最小的元素,请尝试使用冒泡排序。 冒泡排序适用于简单的概念,即在每次传递时将最大元素移动到最后(如果增加顺序)。由于您需要数组中的第一个和第二个最大元素,因此2次冒泡排序将完成。最后一个元素将是最大元素,第二个元素将是第二大元素。 我为您提供的链接可以帮助您了解冒泡排序概念。

http://www.codeido.com/2010/10/bubblesort-written-in-c-with-example-step-by-step/

希望它有所帮助!!!

答案 16 :(得分:-6)

在python中从数组中获取第二大数字是非常容易的,我已经完成了简单的步骤,并放置了各种测试用例,并且每次都给出正确的答案。 PS。我知道这是针对c的,但是我只是给出了一个简单的解决方案,如果在python中完成

n = int(input()) #taking number of elements in array
arr = map(int, input().split()) #taking differet elements
l=[]
s=set()
for i in arr: #putting all the elemnents in set to remove any duplicate number
    s.add(i)
for j in s:  #putting all element from the set in the list to sort and get the second largest number
    l.append(j)
l.sort()
c=len(l)
print(l[c-2]) #printing second largest number