如何获取当前循环的前一个值和后一个值?
我正在做一个热指数计算的项目,项目会从文件 Temperature365.txt 和 Humidity365.txt 中读取温度和湿度的值。如果遇到值为 0 的情况,我希望能用它前面的值和后面的值的平均数来替代这个 0。
举个例子,比如有以下的数值:
34
21
0
42
我希望用 (21+42)/2 来替代 0,而不是用 (21+34)/2。请问我该如何修改这段代码呢?
c1 = -8.78469475556
c2 = 1.61139411
c3 = 2.33854883889
c4 = -0.14611605
c5 = -0.012308094
c6 = -0.0164248277778
c7 = 2.211732 * 10**-3
c8 = 7.2546 * 10**-4
c9 = -3.582 * 10**-6
def whatstatus(hi_val):
if hi_val >= 54:
return "Extreme Danger"
elif 41 <= hi_val < 54:
return "Danger"
elif 32 <= hi_val < 41:
return "Extreme Caution"
elif 27 <= hi_val < 32:
return "Caution"
else:
return "Normal"
def cal_hi(T, H):
Hi = c1 + (c2 * T) + (c3 * H) + (c4 * T * H) + (c5 * (T**2)) + (c6 * (H**2)) + (c7 * (T**2) * H) + (c8 * T * (H**2)) + (c9 * (T**2) * (H**2))
return Hi
def handle_missing_values(data_list):
"""Fills missing values in a list using the average of the previous and next values (if available)."""
if len(data_list) <= 1:
return data_list # Handle edge cases with 0 or 1 elements
output_list = []
for i in range(len(data_list)):
if data_list[i] != 0:
output_list.append(data_list[i])
else:
prev_value = data_list[max(i - 1, 0)] # Safeguard against negative index
next_value = data_list[min(i + 1, len(data_list) - 1)] # Safeguard against exceeding list bounds
if prev_value != 0 and next_value != 0: # Check if both neighbors are valid
output_list.append((prev_value + next_value) / 2)
else:
# Handle cases where only one neighbor is valid (or none)
output_list.append(data_list[i]) # Maintain original value (0)
return output_list
with open('Humidity365.txt') as Hf, open('Temperature365.txt') as Tf:
print("Day\tTemperature(C)\tHumidity(%)\tHeat Index\tStatus", "\n", "---" * 22)
Tlist = []
Hlist = []
for i, (Tl, Hl) in enumerate(zip(Tf, Hf)):
Tx = float(Tl.strip())
Hx = float(Hl.strip())
# Specific fix for line 12 (index 11) using list comprehension
if Hx == 0: # Check for 0 value specifically at index 11
prev_Hx = Hlist[i - 1]
next_Hx = Hlist[i + 1]
Hx = (prev_Hx + next_Hx) / 2 # Calculate average for line 12 only
elif Hx == 0: # Apply the 0-replacement rule to other lines
Hx = handle_missing_values([Hx])[0]
Tlist.append(Tx)
Hlist.append(Hx)
heat_index_val = cal_hi(Tx, Hx)
stat = whatstatus(heat_index_val)
print(f"{i+1}\t{Tx:.2f}\t\t{Hx:.2f}\t\t{heat_index_val:.2f}\t\t{stat}")
if len(Tlist) % 30 == 0:
input("Press <ENTER> to continue")
我希望每次遇到 0 的时候,都能用 (前一个值 + 后一个值) / 2 来替代它。
5 个回答
0
你可以使用enumerate()和列表推导式。假设你列表中的第一个和最后一个元素都不是0,下面的代码应该可以正常工作:
def handle_missing_values(dl):
return [i if i != 0 else (dl[j-1]+dl[j+1])/2 for j,i in enumerate(dl)]
0
你需要把代码拆分开来,并且需要用到两个循环。
- 第一个循环是从文件中读取每一行,创建
Hlist
和Tlist
。 - 然后调用
handle_missing_values
函数两次,来清理Hlist
和Tlist
中的数据。 - 第二个循环用来进行计算,计算
heat_index_val
和stat
,这次是遍历Hlist
和Tlist
。
另外,因为你的 handle_missing_values
函数已经考虑到了特殊情况,所以你不需要再做特别的修复了。
我建议在处理无效值时,可以使用全局平均值或者最近邻的值。如果邻居的值都无效,那就直接把0值去掉再进行后续处理。不过这要看你的具体需求。
顺便提一下,你的 if
和 elif
条件是一样的,对于所有 Hx==0
的情况,代码会尝试访问 i-1
和 i+1
的元素,但 i+1
还没有生成(如果 i=0
的话,i-1
也会出问题)。
0
你可以使用 itertools
来实现这个功能:
import itertools
data = [1, 2, 3, 4, 5, 6, 7]
prev_pool, current_pool, next_pool = itertools.tee(data, 3)
prev_pool = itertools.chain([-1], prev_pool)
next(next_pool)
next_pool = itertools.chain(next_pool, [-9])
for prev_element, current_element, next_element in zip(prev_pool, current_pool, next_pool):
print(f"{prev_element=}, {current_element=}, {next_element=}")
输出结果:
prev_element=-1, current_element=1, next_element=2
prev_element=1, current_element=2, next_element=3
prev_element=2, current_element=3, next_element=4
prev_element=3, current_element=4, next_element=5
prev_element=4, current_element=5, next_element=6
prev_element=5, current_element=6, next_element=7
prev_element=6, current_element=7, next_element=-9
注意事项:
- 我们使用
tee
来把列表分成三个可迭代的部分 - 对于
previous_pool
,我们在前面加上一个值-1
。这个值可以是任何对我们的计算方便的数字 - 对于
next_pool
,我们把池子往前移动,并在后面加上-9
。同样,这个值也可以是任何方便的数字 - 之后,我们可以把这些池子合并在一起,然后逐个遍历它们