'Find max value that is multiple of 3 in an array

Recently, I've got a code test from ABC. Please take a look at this one and give me your idea.

Find the max value of an array of N integers.

E.g. [ 1, -6, 2, 0, 1011, -355]

Require: the max value is a multiple of 3 and the code focuses on the correctness not performance.

def solution(A):
    try:
        if not isinstance(A, list):
            raise TypeError
        max_value = max([x for x in A if x % 3 ==0])
        return max_value
    except Exception as e:
         print(f"{A} is not a list")
         print(e)

So does my code fulfill the requirements or Did I miss any edge case? P/s: They announced that was fail and only got 22/100 pts.



Solution 1:[1]

I think the Exception is bad formulated, it prints "A is not a list" but just put a list like:

a = [ 1, -6, "hi", 0, 1011, -355]

This function will print:

[ 1, -6, "hi", 0, 1011, -355] is not a list

When it is a perfectly valid list.

If you assume that they will only provide a "array(list) of N integers" then the exception pattern makes no sense in the first place, if you assume that you can have bad inputs, then you need to handle a case as the one described.

pd: as a comment pointed out:

["1", "3", "6", "-20"]

Is a list of "integers" (type strings) that will also fail.

Second error:

If they really meant that they will provide an array/np.array then it will also fail in the isinstance as an array is not a list, as others pointed out.

Solution 2:[2]

The question is flawed.

Pure Python doesn't have arrays - it has lists (unless the inquisitor is referring to the array module - which I doubt). However, let's assume that they are synonymous in this context.

Also, the question doesn't tell you what the behaviour should be if there is no answer - i.e., what if none of the numbers in the list are multiples of 3?

Why would you test the input parameter for its type? The question tells you what type it will be.

So I would suggest that it's really simple:

def solution(A):
    return max(x for x in A if x % 3 == 0)

Note that max is passed a generator rather than a list which although not important in this case, is potentially more efficient than building a list

Solution 3:[3]

Honestly I can't see anything wrong with your max code, my guess could be that they are not passing in a list object in their tests - so your check is failing. Instead of testing for list, you could test for iterable.

See:

  1. In Python, how do I determine if an object is iterable?
  2. https://docs.python.org/3/library/functions.html#max
def solution(A):
    try:
        # ensures A is iterable
        _ = iter(A)
        return max([x for x in A if x % 3 ==0])
    except TypeError as e:
        print(f"{A} is not an iterable")
        print(e)

They could, for example, pass a tuple of (-5, 1, 24, 6), which would fail in your implementation.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2
Solution 3