I've realized that I've actually seen code use a trick to enable exactly this optimization in the past, without needing language extensions (although I don't remember where). Taking two of my motivating examples from elsewhere in the thread:
bc = b*c a = bc + d
f = get_f_long_name(x) g = get_g_long_name(del f) h = get_h_long_name(del g)
This can be written today with exactly the intended semantics by using lists and pop:
bc = [b * c] a = bc.pop()
f = [get_f_long_name(x)] g = [get_g_long_name(f.pop())] h = get_h_long_name(g.pop())
I'd argue that this is a little less readable, but it makes the incremental improvement provided by a language change less significant, which makes the change harder to justify.