Python Forum
If with For statement shorthand?
Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
If with For statement shorthand?
#1
Is there a way to reduce code down?

for x in resources:
            if resources[x] < MENU[option]["ingredients"][x]:
                print(f"Sorry there is not enough {x}")
                resources_sufficient = False
I was thinking something like this, but obviously this doesn't work

if resources[x] < MENU[option]["ingredients"[x] for x in resources:
            print(f"Sorry there is not enough {x}")
            resources_sufficient = False
Reply
#2
It is custom to indent 4 spaces.

I cannot think of a way to reduce the code and still have it perform the same way. If you don't mind it doing something slightly different.
not_enough = [x for x in resources if resources[x] < MENU[option]["ingredients"][x]]
print(f"Sorry there is not enough {', '.join(not_enough)}")
resources_sufficient = len(not_enough) > 0
It doesn't shrink it down much.
Reply
#3
I think you have four separate ideas (the resources to examine, the conditional, the information to the user, the status for later), so putting that on four separate lines seems completely reasonable.

You could use a list comprehension, but I wouldn't necessarily prefer it.

insufficient_resources = [k for k,v in resources.items() if v < MENU[option]["ingredients"][k]]
if insufficient_resources:
    print(f"Sorry there is not enough {','.join(insufficient_resources)}")

# or
insufficient_resources = [k for k,v in resources.items() if v < MENU[option]["ingredients"][k]]
for ingredient in insufficient_resources:
    print(f"Sorry there is not enough {ingredient}")
Rather than setting resources_sufficient as a separate variable, you can just test the truthiness of insufficient_resources.
Reply
#4
I think your code is backward. Your logic crashes if your resources contains ingredients that are not in MENU[option]["ingredients"]. In other words, each recipe on your menu must use every ingredient in your inventory (resources).

I would do this:
ingredients = {"A": 10, "B": 15}
resources = {"A": 11, "B": 5, "C": 5}

resources_sufficient = not any(
    [x for x in ingredients
        if resources[x] < ingredients[x]
    ]
)
print(resources_sufficient)
Output:
Sorry there are not enough B True
Well, I wouldn't really do that because the comprehension is mostly used for a side effect, and that is bad programming. I would write it this way:
ingredients = {"A": 10, "B": 15}
resources = {"A": 11, "B": 5, "C": 5}

missing_ingredients =  [x for x in ingredients if resources[x] < ingredients[x]]
if missing_ingredients:
    print("You are missing", ",".join(missing_ingredients))
And use missing_ingredients for it's bool equivalent (False if empty, else True).
Reply
#5
Thank you so much for all your wonderful replies!

I had seen examples where list comprehension shorted code down so much that I was hoping there was a way to do it here.

Thank you to those who gave suggestions for the overall program as well. I'm really just trying to get my head wrapped around some of the little details of the coding before moving on to my next lesson. But thank you still

Jamie
Reply
#6
I would favour
missing_ingredients = [
    x for (x, needs) in MENU[option]['ingredients'].items() if needs > resources.get(x, 0)]
Now if you only want to know if at least one ingredient is missing, choose
if any(needs > resources.get(x, 0) for x, needs in MENU[option]['ingredients'].items()):
    print("At least one ingredient is missing.")
Reply


Possibly Related Threads…
Thread Author Replies Views Last Post
  'namespace' shorthand for function arguments? shadowphile 5 2,659 Aug-11-2021, 09:02 PM
Last Post: shadowphile
  cant understand the logic behind shorthand form of operator pradeep_sn 2 1,781 May-20-2020, 06:53 PM
Last Post: buran

Forum Jump:

User Panel Messages

Announcements
Announcement #1 8/1/2020
Announcement #2 8/2/2020
Announcement #3 8/6/2020