3
  1. User inputs positive int value (number);
  2. User prints number int values;
  3. Need to find max value and print it.

My code is

#include <stdio.h>

int main() {
    int number;
    int max;
    int temp;

    scanf("%d", &number);
    scanf("%d", &max);

    for ( int i = 1; i < number; i++ ) {
        scanf("%d", &temp);
        if ( temp > max ) {
            max = temp;
        }
    }

    printf("%d\n", max);
    return 0;
}

This works but online test tool says i need to optimize code, because it uses too many operations. Arrays are forbidden. Can only use stdio.

14
  • 3
    What is the point of scanf("%d", &max);? Commented Jun 25, 2012 at 10:23
  • 2
    Set max to INT_MIN (from <limits.h>) initially, don't input it. If you're going to ask the user for the max, there's no point in writing a program to find it, is ther? Commented Jun 25, 2012 at 10:24
  • 4
    @unwind - Actually, OP uses max to input the first number, then inputs the next number - 1 numbers in a loop. i.e. its just a weird way to write this program, but it is functionally correct. Commented Jun 25, 2012 at 10:26
  • 2
    I don't think that that problem could be solved with less operations ...? Commented Jun 25, 2012 at 10:30
  • @ArjunShankar Aah, good point, didn't realize that. Thanks. Commented Jun 25, 2012 at 10:33

6 Answers 6

4

By using Duff's device you could save some comparisons in the for-loop. It'd be a bad practice, but maybe that's what you are expected to do.

#include <stdio.h>

int main (void) {
    unsigned max = 0;
    unsigned length;
    scanf("%u", &length);

    unsigned temp = 0;
    unsigned iterations = (length+8-1) / 8;
    switch (length % 8) {
        case 0: do { scanf("%u", &temp); if (temp > max) max = temp;
        case 7:      scanf("%u", &temp); if (temp > max) max = temp;
        case 6:      scanf("%u", &temp); if (temp > max) max = temp;
        case 5:      scanf("%u", &temp); if (temp > max) max = temp;
        case 4:      scanf("%u", &temp); if (temp > max) max = temp;
        case 3:      scanf("%u", &temp); if (temp > max) max = temp;
        case 2:      scanf("%u", &temp); if (temp > max) max = temp;
        case 1:      scanf("%u", &temp); if (temp > max) max = temp;
                } while (--iterations > 0);
    }

    printf("%u\n", max);
    return 0;
}

I used unsigned ints, because you said you only have positive numbers. The code assumes that the sequence has at least one element.

Update 1:

Example using manual loop unrolling. That's an even worse practice than Duff's device. Maybe the testing tool you got will like it, but you should never use this code to impress a potential employer!

#include <stdio.h>

int main (void) {
    signed max = -0x80000000;
    unsigned length;
    scanf("%u", &length);

    signed temp;
    for (; length >= 8; length -= 8) {
        scanf("%d", &temp); if (temp > max) max = temp;
        scanf("%d", &temp); if (temp > max) max = temp;
        scanf("%d", &temp); if (temp > max) max = temp;
        scanf("%d", &temp); if (temp > max) max = temp;
        scanf("%d", &temp); if (temp > max) max = temp;
        scanf("%d", &temp); if (temp > max) max = temp;
        scanf("%d", &temp); if (temp > max) max = temp;
        scanf("%d", &temp); if (temp > max) max = temp;
    }
    if (length > 4) {
        scanf("%d", &temp); if (temp > max) max = temp;
        scanf("%d", &temp); if (temp > max) max = temp;
        scanf("%d", &temp); if (temp > max) max = temp;
        scanf("%d", &temp); if (temp > max) max = temp;
        length -= 4;
    }
    for (; length > 0; --length) {
        scanf("%d", &temp); if (temp > max) max = temp;
    }

    printf("%d\n", max);
    return 0;
}

Update 2:

You stated that your evaluation tool likes it if scanf is less often called, so:

#include <stdio.h>
int main (void) {
    signed max = -0x80000000;
    unsigned length;
    scanf("%u", &length);

    signed t1, t2, t3, t4, t5, t6, t7, t8;
    for (; length >= 8; length -= 8) {
        scanf("%d%d%d%d%d%d%d%d", &t1, &t2, &t3, &t4, &t5, &t6, &t7, &t8);
        if (t1 > max) max = t1;
        if (t2 > max) max = t2;
        if (t3 > max) max = t3;
        if (t4 > max) max = t4;
        if (t5 > max) max = t5;
        if (t6 > max) max = t6;
        if (t7 > max) max = t7;
        if (t8 > max) max = t8;
    }
    if (length > 4) {
        scanf("%d%d%d%d", &t1, &t2, &t3, &t4);
        if (t1 > max) max = t1;
        if (t2 > max) max = t2;
        if (t3 > max) max = t3;
        if (t4 > max) max = t4;
        length -= 4;
    }
    for (; length > 0; --length) {
        scanf("%d", &t1); if (t1 > max) max = t1;
    }

    printf("%d\n", max);
    return 0;
}
Sign up to request clarification or add additional context in comments.

4 Comments

positive was about the number of elements only
@unkulunkulu, I read it wrong, sorry. I leave the task for OP to change it back to signed. ;-)
thanks for response. tool doesn't work with case-switch and do-while. Is its possible to remake this with if-else and for or i should just commit suicide?
@user1479645 now using manual loop unrolling.
2

I'd like to know what test tool says you have too many operations that isn't some code golf competition. Also, what the number of acceptable operations is and how they define 'operation'.

#include <stdio.h>

int main() {
    int numbersLeft,
        number,
        max = 0;

    scanf("%d", &numbersLeft);

    while ( numbersLeft-- ) {
        scanf("%d", &number);
        max = number > max? number: max;
    }

    printf("%d\n", max);
    return 0;
}

7 Comments

Sure, use INT_MIN instead of 0
That's why I asked how they define operation. Is it the number of operands the code compiles to or is it the number of instructions used to run through a list.
With code i posted. Test tool says "161 operations". If set max to "-2147483647 - 1" then its "174 operations". i can't use limits.h
Right. We don't know what an 'operation' is here. But if anything, inputting the first number into max will reduce the number of 'operations', or keep it the same (as per any definition of operation). I like your answer, but I really would like it if you do this too.
@SpacedMonkey - It is unfortunate that students are being judged on meaningless, unexplained criterion, with meaningless restrictions. Anyway, you reduced an 'operation' (IMO), by getting rid of a loop initializer. For this, +1.
|
2

Your 'test tool' is probably broken, or expects you to do meaningless micro-optimizations while making code hard to read, which the compiler will do anyway.

  1. You need to ask the user for the number of numbers => 1 scanf. You did this.
  2. Next you need to ask the user for number numbers => scanf, number times. You did this.
  3. Next you need to find the largest => loop number times, and compare. You already achieved this in the same loop as the previous one. And you did it well because you did the minimum possible number - 1 comparisons.
  4. Next you need to print the result => 1 printf. You did this too.

This is the fastest you can possibly get[1]. There is no scope for 'optimization'.

[1] If you had 2 cores, and were writing a multi-threaded program, you could do step 2 and 3 faster by pipelining them (see unkulunkulu's comments for why this is the fastest you can get).

10 Comments

parallelizing couldn't help here, this comparison will be pipelined easily. Computing maximum while reading from file has zero overhead.
Thanks for response. With code i posted. Test tool says "161 operations". If set max to "-2147483647 - 1" then its "174 operations". I don't know if its broken. I REALLY need to pass this task, my life depends on it.
@unkulunkulu - Depends. I could split the loop into 2, input in the first, and then compare parallely in the second. With more than 2 CPUs, and enough input, this could be much faster than a pipeline.
How does the tool work? You upload the .c file, or you upload a binary?
@ArjunShankar, once again, reading while comparing is not slower than just reading. Not even a microsecond slower, that comparison doesn't add anything, and I bet you cannot scan all the numbers faster. Even 1-core processor is a parallel thing, it makes these comparisons in parallel.
|
2

Should have used 1 scanf() instead of two:

#include <stdio.h>

int main() {
    int number;
    int max;
    int temp;

    scanf("%d %d", &number, &max);
    for ( int i = 1; i < number; i++ ) {
        scanf("%d", &temp);
        if ( temp > max ) {
            max = temp;
        }
    }
    printf("%d\n", max);
    return 0;
}

Sorry, and thanks to everyone! Hugs and kisses!

Comments

1

You don't really need the i variable: you can use number itself.

Also you may want to abuse the for statement :)

#include <stdio.h>

int main(void) {
    int number;
    int max;
    int temp;

    for (scanf("%d", &number), scanf("%d", &max)
       ; --number && scanf("%d", &temp)
       ; )
    {
        if (temp > max) max = temp;
    }

    printf("%d\n", max);
    return 0;
}

1 Comment

So we know you need to scanf("%d", &max); before the for() but @pmg still has a point. Get rid of i by using for ( ; --number; )
-1
#include <stdio.h>

int main() {
    int number;
    int max;
    int temp,i;

    scanf("%d", &number);

    for ( i = 0; i < number; i++ ) {
        scanf("%d", &temp);
        if(i==0)
            max=temp;
        if ( temp > max ) {
            max = temp;
        }
    }

printf("max=%d\n", max);
return 0;

}

2 Comments

Compliance with the conditions?
Does not meet the conditions?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.