-2

I created a fairly simple function; however, it isn't performing as desired. I think i'm missing something with my if line but not sure.

I have two lists. I want to take the first number of list 1 and see if it is the same number as the first number in list 2. Then I want to do that all the way through.

I should end with 17 'Yes' responses in my list (l)

preds = [1, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0, 0, 1]
labels = [1, 0, 0, 1,  0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1,  0, 1]



def fix(x,y):
    l = []
    for i in x:
        if i == y:
            l.append('yes')
        else:
            l.append('no')
    return(l)


fix(labels, preds)
Evan Day
  • 23
  • 4
  • `if i == y` is comparing a number to a list, which will always be False. Did you mean to use `if i == y[0]` ? – sj95126 Jul 31 '22 at 23:02
  • 1
    `i` is going to be an element of `x`, which is an integer. An integer will never be equal to a list. You need `zip` here. `for i,j in zip(x,y):` / `if i == j:` – Tim Roberts Jul 31 '22 at 23:02
  • Why do you expect 17x "yes"? The first 17 elements of `pred` do not match `labels`? You are looping over the elements of the first list `x`, but comparing each element to the entire list `y` with `if i == y`, so that will never work. – Grismar Jul 31 '22 at 23:03
  • Does this answer your question? [How can I compare two lists in python and return matches](https://stackoverflow.com/questions/1388818/how-can-i-compare-two-lists-in-python-and-return-matches) – David Foster Jul 31 '22 at 23:04
  • 1
    If you expect 17x "yes", perhaps what you're really try to do is determing if the elements of `labels` all appear in `preds`, in the same order, but with optional extra elements added in at arbitrary locations? – Grismar Jul 31 '22 at 23:05
  • Hmm... I think Tim's right, but the first 17 elements don't match. There are some extra spaces though, so maybe you forgot some elements? – wjandrea Jul 31 '22 at 23:13
  • Possible duplicate: [How do I iterate through two lists in parallel?](/q/1663807/4518341) – wjandrea Jul 31 '22 at 23:20
  • Please explain the rationale behind an output list containing 17 'Yes' elements from these data – DarkKnight Aug 01 '22 at 06:13

2 Answers2

0

You are comparing the elements of x to the variable holding list y, which will always be false. To accomplish this easiest in a pythonic way use zip, as below:

preds = [1, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0, 0, 1]
labels = [1, 0, 0, 1,  0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1,  0, 1]



def fix(x,y):
    l = []
    for i,j in zip(x,y):
        if i == j:
            l.append('yes')
        else:
            l.append('no')
    return l


fix(labels, preds)

Zip returns a tuple with the elements of each list at a given index: https://www.programiz.com/python-programming/methods/built-in/zip

Here is a list comprehension that does what you want in one line:

['yes' if i == j else 'no'  for i, j in zip(preds, labels)]
nklisch
  • 76
  • 3
  • parentheses after `return` are redundant and you could just `return ["yes" if i == j else "no" for i, j in zip(x, y)]` although I guess it's not as readable, but also it's pointless to simply call that function, you should assign the returned value to some name or at least print it – Matiiss Jul 31 '22 at 23:15
  • Ya, I just copy pasted the original and modified what was needed. I could have cleaned it up more, but why do that when trying to help someone just understand something like this? – nklisch Jul 31 '22 at 23:21
  • because good coding practices are good coding practices – Matiiss Jul 31 '22 at 23:22
  • I'm talking about the parentheses after `return`, they are redundant and thus should be removed, it doesn't even change their code that much, I already said that that list comp is not as readable but there are other good coding practices/conventions that could/should be applied, such as not using redundant parentheses, using double quotes (just commonly used in major Python libraries, thus a convention), having space after comma – Matiiss Jul 31 '22 at 23:36
  • Fair, I added a secondary list comprehension solution to show how it should really be done – nklisch Jul 31 '22 at 23:36
  • 2
    @Matiiss if you have nothing constructive to contribute, it's best not to comment at all. The list comprehension appears to create exactly the same list as returned by the function. Use nklisch is not wrong if they try to only change the element that matters for understanding - if the answer doesn't hold up to good coding standards, that can certainly be pointed out, but it's not the point of the answer, and won't help OP more. The real question here is if this actually solves OP's problem, but they can comment on that themselves. – Grismar Aug 01 '22 at 00:34
  • @Grismar when I added that comment the list comp didn't do what the function did also I'm not saying they're wrong, the answer answers the question I just dislike conventions not being followed (more so the major parts of it) – Matiiss Aug 01 '22 at 15:54
0

If you wanted to see if all element of one list appear in another list in that order (with possible extra elements in the second list), this would be an approach:

preds = [1, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0, 0, 1]
labels = [1, 0, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1]


def contained_in_order(xs: list, ys: list) -> bool:
    i = 0
    try:
        for x in xs:
            i = ys.index(x, i) + 1
        return True
    except ValueError:
        return False


print(contained_in_order(labels, preds))

This prints True for the lists you provided as labels is indeed contained in pred in order.

Howevever, a list of 'yes' and 'no' values wouldn't make sense in this context, since there may be many ways to match. For example, consider:

preds = [1, 0, 1]
labels = [0, 0]

Clearly, labels is not contained in preds in order. But both [1, 0] and [0, 1] would be. So should the result be ['yes', 'no'] or ['no', 'yes']?

You could write a function that generates all possible mismatches, but I doubt that's what you're after. Perhaps you can update the question to clarify what exactly you're trying to achieve, or comment on the answer.

Edit: If you're just after a list of matches, which you say you'd like to see as strings, this is all you need:

preds = [1, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0, 0, 1]
labels = [1, 0, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1]

yes_no = ['yes' if p == l else 'no' for p, l in zip(preds, labels)]
print(yes_no)

Output:

['yes', 'yes', 'yes', 'yes', 'no', 'no', 'no', 'yes', 'no', 'yes', 'no', 'yes', 'yes', 'yes', 'no', 'no', 'yes']
Grismar
  • 27,561
  • 4
  • 31
  • 54
  • thank you all for the feedback (well, almost all of you = ) ). @Grismar to answer your question the desired result would be 'no' , 'yes. maybe this will help. I want to see if the first element in list 1 is equal to the first element in list 2..if so, return Yes to a new list. Then I want to see if the second element in my first list is equal to the second element in the second list...if so, return Yes to my list and so on. – Evan Day Aug 01 '22 at 19:29
  • If that's all you needed, you should have responded to the comments - in your question you say you expect 17x 'yes', which you wouldn't get because the lists clearly don't match. Several people asked for an explanation, but you remained silent. I've updated the answer, but am also voting to close the question because it's entirely unclear as it is. – Grismar Aug 01 '22 at 22:32
  • lol - sorry for any confusion, I'm pretty new to posting on this site, i mostly just search for my answers. I do my best to answer in a timely manner. I believe I marked your response as the answer? either way, have a great night = ) – Evan Day Aug 02 '22 at 01:04
  • That's alright, we all have to learn - just keep in mind that the rules on StackOverflow aren't arbitrary or needlessly strict. In a professional environment, you also don't want to waste your colleagues time by having them ask obvious questions you should have the answers to already, or by asking them for something you don't really need, and then for them to have to go and redo the work once you tell them what you actually need. StackOverflow enforces rules that apply to a professional software development environment and it's better learn about them here than on the job. – Grismar Aug 02 '22 at 03:16