Exercise 3.1
Casing String Inventory
A well's casing program is a sequence of strings of pipe of decreasing diameter, each set at a planned depth. Once each casing is in the ground, it cannot be moved; the data describing it is permanent. That makes a tuple the right container.
Build the casing program as a list of tuples in this exact field order: (name, od_in, weight_lb_ft, grade, setting_depth_ft).
| Casing | OD (in) | Weight (lb/ft) | Grade | Setting depth (ft) |
|---|---|---|---|---|
| Conductor | 36 | 192 | X-52 | 500 |
| Surface | 20 | 94 | K-55 | 2,800 |
| Intermediate | 13.375 | 68 | L-80 | 6,500 |
| Production | 9.625 | 47 | L-80 | 9,800 |
| Liner | 7 | 29 | P-110 | 12,400 |
Then write casing_at_depth(depth_ft) that returns the name of the casing string set at or above a given depth (i.e. the deepest string whose setting depth is ≥ the target depth. (At 4,000 ft, the next casing above you is the Intermediate at 6,500 ft.)
Stuck? Reveal hints one at a time — they progress from nudge to near-solution.
visibilityReveal reference solutionexpand_more
Try solving it yourself first — the hints walk you through it. The solution below is one valid approach; yours may differ and still be correct.
casing_program = [
("Conductor", 36, 192, "X-52", 500),
("Surface", 20, 94, "K-55", 2800),
("Intermediate", 13.375, 68, "L-80", 6500),
("Production", 9.625, 47, "L-80", 9800),
("Liner", 7, 29, "P-110", 12400),
]
def casing_at_depth(depth_ft):
candidates = [row for row in casing_program if row[4] >= depth_ft]
if not candidates:
return None
return min(candidates, key=lambda row: row[4])[0]
for d in (4000, 9500, 12000, 300):
print(f"At {d:>6,} ft → {casing_at_depth(d)}")
lockCopying code is a Full Access feature.