Sal's Shipping Project Troubles

I had a ton of trouble with the syntax for this project. I watched the video for the project walkthrough, but felt very uncomfortable with the fact that the solution was so different than anything I’ve seen in the lessons so far. In the end, because I couldn’t get my own method to work, I copied the method in the video with very slight modifications. The code runs well now, but each time it prints I see an extra line that says “None”. Please help me figure out why this is happening and how I can fix it! Thank you so much :slight_smile:

Hi @kgnunn999,

The extra None is not your fault. Due the to manner in which Codecademy handles submitted code for this exercise, the return value of the cheapest_shipping function gets displayed. Since we have not explicitly supplied a return value, it defaults to None.

You could add a return statement as the final line in the function. Try this as an example, making sure it is indented appropriately to be part of the function, but not part of the else block …

  return "Thanks for choosing Sal's Shipping!"

You could do this instead …

  return cost
2 Likes

It would be interesting to see your code that didn’t work. That at least may help us arrive at some talking points rather than critically analyzing the given solution.

Sal’s Shipping

Please post your unaccepted code, and any error messages that were generated by it. I think you could get something more from this question by doing so.


Silliness segue…

def ground_shipping(weight):
  return 20 + g_rates[tabs.index([x for x in tabs if weight > x][-1])] * weight

def drone_shipping(weight):
  return d_rates[tabs.index([x for x in tabs if weight > x][-1])] * weight

tabs = [0, 2, 6, 10]
g_rates = [1.50, 3.00, 4.00, 4.75]
d_rates = [4.50, 9.00, 12.00, 14.25]
print ("{:.2f}".format(ground_shipping(8.4)))
print ("{:.2f}".format(drone_shipping(1.5)))
53.60
6.75

See any repetition in the above? It’s my usual harp, avoid duplication and repetition, so this means a helper function is in good order.

def get_rate_index(weight):
  return tabs.index([x for x in tabs if weight > x][-1])

so that,

def ground_shipping(weight):
  return 20 + g_rates[get_rate_index(weight)] * weight

def drone_shipping(weight):
  return d_rates[get_rate_index(weight)] * weight

Funny… The only function to contain an if statement is the helper. A major paradym shift in control flow. This is not elementary code. Far from it; but, you now have experienced a different view of how DATA can be processed with minimal logic as long as we set up the criteria and constraints. In a sense this program is merely an inverse or yours.


One thing above that rubs me the wrong way is the number literal inside the ground_shipping function. We can replace that with a parameter, or with a global. In this instance, since all the data is global, we may as well add this to the global data pool.

base_rate = 20
  return base_rate + g_rates[get_rate_index(weight)] * weight

In case you’re wondering, the work we’ve been doing here is called, refactoring. We could not have got here without the naive code. Stick with that model while you learn. I mean it. Ignore (but bookmark) this example until you are done this course, then come back to it.

For now, we still wish to see what attempts you have made, thus far…

@alyssavigil if we could get coach input here it would be invaluable. Someone needs to explain the value of naive code.

1 Like

Thank you! I’ll give that a shot!

Wow, my head is spinning! I’ll definitely have to come back to this one at a later date to see if I can understand it. As for the original flawed code of mine, I’ll have to restart the project and try to remember what it is I did. I would like to know why it didn’t work…

Was your code not accepted by the SCT? Did it raise any errors? What was it doing/not doing according to expectations?

As for my example above, ignore it until you finish the unit on Advanced Topics.

Since this is a project rather than a lesson, Codecademy does not subject it to an SCT. However, the Python interpreter could, of course, raise an error, if something is wrong.

3 Likes

Thank you so much for this I’ve been tearing my hair out trying to figure it out!

Some of these videos are frustrating because the solutions shown in the videos weren’t covered in the lessons. It was especially frustrating in this video because the alternate method used by the presenter didn’t even seem to be more efficient. It was just over complicated for no reason. Here is the solution I used for the whole project. Hopefully this helps some of you. It doesn’t have anything in it that was not covered in the lessons.

def cost_of_ground_shipping(weight):

if weight <= 2:
    price_per_pound = 1.50
elif weight <= 6:
    price_per_pound = 3.00
elif weight <= 10:
    price_per_pound = 4.00
else:
    price_per_pound = 4.75
return (price_per_pound * weight) + 20

print(cost_of_ground_shipping(8.4))

shipping_cost_premium = 125.00

def cost_of_drone_shipping(weight):

if weight <= 2:
    price_per_pound = 4.50
elif weight <= 6:
    price_per_pound = 9.00
elif weight <= 10:
    price_per_pound = 12.00
else:
    price_per_pound = 14.25
return price_per_pound * weight

print(cost_of_drone_shipping(1.5))

def cheapest_method(weight):

ground = cost_of_ground_shipping(weight)
premium = shipping_cost_premium
drone = cost_of_drone_shipping(weight)

if ground < premium and ground < drone:
    print("Ground shipping is cheapest and will cost...")
    print(ground)
elif premium < ground and premium < drone:
    print("Premium shipping is the cheapest and will cost...")
    print(premium)
elif drone < ground and drone < premium:
    print("Drone shipping is the cheapest and will cost...")
    print(drone)

(cheapest_method(4.8))
(cheapest_method(41.5))

3 Likes

It doesn’t format the cost into proper form but we weren’t taught how to do that yet.

1 Like

C’mon Code Academy, you can do better - THIS VIDEO SOLUTION HAS MATERIAL NOT COVERED IN THE LESSON I realize it’s not a stretch, but come on …a beginner (like me) is not looking to make inferences off what we’ve learned. I am looking to apply what we have learned at this point to the problems we’ll get.

2 Likes

It’s super frustrating to be stuck and the solution is past what you have learned. Feels like a bait and switch when you’re trying to solve a problem based on past lessons.

3 Likes

Here is what I typed in the IDE, and I got it correct!
#Since weight is going to be used in one of the variable assigning, declaring it as a variable first would avoid a NameError Error.
weight = 0.0
premium = 125.00

def gt_cost_finder(weight):
cost = weight * 4.00 + 20.00
return cost

ground = gt_cost_finder(weight)

def dt_cost_finder(weight):
cost = weight* 4.50
return cost

drone = dt_cost_finder(weight)

def cheapest_finder(weight):
if gt_cost_finder(weight) < dt_cost_finder(weight) and gt_cost_finder(weight) < premium:
return "Ground, " + str(gt_cost_finder(weight))
elif dt_cost_finder(weight) < gt_cost_finder(weight) and dt_cost_finder(weight) < premium:
return "Drone, " + str(dt_cost_finder(weight))
elif premium < dt_cost_finder(weight) and premium < gt_cost_finder(weight):
return "Premium, " + str(premium)

print(cheapest_finder(41.5))

This below code works fine, but is there any way for the result to have a zero at the 2nd decimal place if there is no digit after the first decimal place?

def norm_gscost(weight):
  if weight <= 2:
    rate = 1.50
  elif weight <= 6:
    rate = 3.00
  elif weight <= 10:
    rate = 4.00
  else:
    rate = 4.75
  cost = 20 + weight * rate  
  return cost
print(norm_gscost(11))

prem_gscost = 125.00

def dscost(weight):
  if weight <= 2:
    rate = 4.50
  elif weight <= 6:
    rate = 9.00
  elif weight <= 10:
    rate = 12.00
  else:
    rate = 14.25
  cost= 0.00 + weight * rate
  return cost
print(dscost(1.5))

def cheapest_shipping(weight):
  norm = norm_gscost(weight)
  prem = prem_gscost
  drone = dscost(weight)
  if norm < prem and norm < drone:
    return "Ground Shipping is the cheapest and it will cost you $" + str(norm) +"."
  elif prem < drone and prem < norm:
    return "Premium Ground Shipping is the cheapest and it will cost you $" + str(prem) +"."
  elif drone < norm and drone < prem :
    return "Drone Shipping is the cheapest and it will cost you $" + str(drone) + "."
  
print(cheapest_shipping(4.8))
print(cheapest_shipping(41.5))
  

The printed results:

72.25
6.75
Ground Shipping is the cheapest and it will cost you $34.4.
Premium Ground Shipping is the cheapest and it will cost you $125.0.

There, $34.4 and $125.0 just look odd. Is there any way to make them look like $34.40 and $125.00

Why, yes. Yes there is. There are likely many ways. I’m not sure if you are familiar yet with the string.format() method, but it will do the trick. I altered the return statements in your code like so:

  if norm < prem and norm < drone:
    return "Ground Shipping is the cheapest and it will cost you {}.".format('${:.2f}'.format(norm))
  elif prem < drone and prem < norm:
    return "Premium Ground Shipping is the cheapest and it will cost you {}.".format('${:.2f}'.format(prem))
  elif drone < norm and drone < prem :
    return "Drone Shipping is the cheapest and it will cost you {}.".format('${:.2f}'.format(drone))

and printed this output:

72.25
6.75
Ground Shipping is the cheapest and it will cost you $34.40.
Premium Ground Shipping is the cheapest and it will cost you $125.00.

Happy coding!

I tried like that but still I get " File “script.py”, line 2
if weight <= 2:
^
IndentationError: expected an indented block"
I really can’t work it out!

Hello, @digital3191190673.

Welcome to the forum.

This error occurs when you start an if statement, but don’t have any code to execute when the condition is true. For example:

a = 5

if a < 6:
    return a + 10 #returns 15

if a > 5:
return a * 2 #throws IndentationError
1 Like