-1

In the following code user enters N pair of inputs each time. When users enter value 2, the most recent tuple will be deleted and value 3 prints the max of 2nd element of remaining tuples . Assume the input list is B=[(1,4),(1,37),2,3,(1,29),3]. Therefore, 2 will remove (1,37). Then (1,4) remains on the list then 3 prints value 4 of (1,4). By entering (1,29) remaining list will be ([1,4],[1,29]) and code should print the max of 2nd element in tuples which is 29 but it prints 4 instead of 29.

So expected output is:

4
29

But my code output is:

4
4
N = int(input())
inputs = []
for i in range(N):
    inputs.append(input().split())
B = []
for b in inputs:
    if len(b) == 2:
        B.append(b)
    if b == ['2']:
        del B[-1]  
    if b == ['3']:
        print(max(B,key=lambda x:x[1])[1])
  • 1
    Does this answer your question? [How to sort a list of strings numerically?](https://stackoverflow.com/questions/3426108/how-to-sort-a-list-of-strings-numerically) – mkrieger1 Oct 04 '20 at 18:44

2 Answers2

0

Simple correction:

'4' > '29' but 4 < 29

So:

print(max(B,key=lambda x:x[1])[1]) should be print(max(B,key=lambda x:int(x[1]))[1])

Alternatively, and better, is to convert the strings to integers upon input and then your lambda function would be correct.

Most Efficient Method (I can think of)

This code should give superior performance. Test it thoroughly:

N = int(input())
inputs = [[int(x) for x in input().split()] for _ in range(N)]

max_values = []
B = []
for t in inputs:
    if len(t) == 2:
        B.append(t)
        v = t[1]
        if not max_values or v >= max_values[-1]: # if it's smaller, it can never be a maximum value
            max_values.append(v)
    elif t == [2]:
        item = B.pop() # remove last element
        v = item[1]
        if v == max_values[-1]:
            max_values.pop()
    else:
        assert t == [3]
        print(max_values[-1])
Booboo
  • 38,656
  • 3
  • 37
  • 60
  • Thanks for catching the problem. Do yo have any idea to speed up the code since the inputs are entering by robot and can be thousands. I need it to run less than 5 sec. –  Oct 04 '20 at 18:49
  • 1
    Are they actually input via an `input` statement and where the first number entered is the number lines of input to follow? I would need to know precisely how the input is done. – Booboo Oct 04 '20 at 18:59
  • The first input is number of lines. Inputs are entered by user like this: first input is '6' in this case and then user press enter to go next line an type '1 4' and again press enter and type '1 37' and so on... –  Oct 04 '20 at 19:04
  • It prints "4" inside the input loop after user entering first "3" –  Oct 04 '20 at 19:28
  • 1
    I mentioned that it doesn't wait for all the input before it starts printing results. I've updated answer with a third variation that does (has a bit more storage overhead). – Booboo Oct 04 '20 at 19:32
  • 1
    Test this against something larger than 3 or 4 tuples and smaller than thousands.(unless the results are easily verified) – Booboo Oct 04 '20 at 19:37
  • The speed has dramatically increased! But it seems there is a bug in code since output of some test cases are wrong. –  Oct 04 '20 at 19:42
  • Let us [continue this discussion in chat](https://chat.stackoverflow.com/rooms/222496/discussion-between-booboo-and-user14385051). – Booboo Oct 04 '20 at 19:58
0

Check if the element is a tuple and check the integers without quotes or a list

#N = int(input())
#inputs = []
inputs = [(1,4),(1,37),2,3,(1,29),3]
#for i in range(N):
#    inputs.append(input().split())

B = []
for b in inputs:
    if type(b) == tuple:
        B.append(b)
    if b == 2:
        del B[-1]  
    if b == 3:
        print(max(B,key=lambda x:x[1])[1])

Output

4
29
Mike67
  • 11,175
  • 2
  • 7
  • 15