列表列表 - 比较相邻值,如果第二个元素相同 - 取旧的
List of lists - Compare neighboring values and IF second elements are the same - take older one
我正在尝试为这个任务找到一个更优雅的解决方案:我们有一个包含日期和值对的列表列表 -> 需要与邻居值进行比较并且如果值相同 - 我们只选择最早的日期(但它只适用于近邻)。
l = [[datetime.datetime(2021, 1, 1, 0, 0), 0],
[datetime.datetime(2021, 3, 1, 0, 0), 0], # need to skipp
[datetime.datetime(2021, 4, 1, 0, 0), 2],
[datetime.datetime(2021, 8, 1, 0, 0), 0], # keep!
[datetime.datetime(2021, 10, 1, 0, 0), 5]]
预期结果:
[datetime.datetime(2021, 1, 1, 0, 0),
datetime.datetime(2021, 4, 1, 0, 0),
datetime.datetime(2021, 8, 1, 0, 0),
datetime.datetime(2021, 10, 1, 0, 0)]
请看一个例子,看看我是如何解决这个问题的。非常感谢任何关于如何优化它的想法!
def get_dates_1(): # solution 1 with reverse
l = [[datetime.datetime(2021, 1, 1, 0, 0), 0],
[datetime.datetime(2021, 3, 1, 0, 0), 0], # need to skip
[datetime.datetime(2021, 4, 1, 0, 0), 2],
[datetime.datetime(2021, 8, 1, 0, 0), 5],
[datetime.datetime(2021, 10, 1, 0, 0), 5]] # need to skip
l.reverse()
dates = []
for i in range(len(l)):
if i < len(l) - 1:
if l[i][1] != l[i + 1][1]:
dates.append(l[i][0])
else:
dates.append(l[i][0])
return list(reversed(dates))
def get_dates_2(): # solution 2 w/o reverse
l = [[datetime.datetime(2021, 1, 1, 0, 0), 0],
[datetime.datetime(2021, 3, 1, 0, 0), 0], # need to skip
[datetime.datetime(2021, 4, 1, 0, 0), 2],
[datetime.datetime(2021, 8, 1, 0, 0), 5],
[datetime.datetime(2021, 10, 1, 0, 0), 5]] # need to skip
l.sort(key=lambda x: x[0])
result = [l[0]]
for date, value in l:
if value != result[-1][1]:
result.append([date, value])
dates = [x for x, _ in result]
return dates
预计:
[datetime.datetime(2021, 1, 1, 0, 0),
datetime.datetime(2021, 4, 1, 0, 0),
datetime.datetime(2021, 8, 1, 0, 0)]
我的解决方案使用 itertools.groupyby
将列表分成子组。
import datetime
import itertools
def get_dates():
my_list = [
[datetime.datetime(2021, 3, 1, 0, 0), 0],
[datetime.datetime(2021, 1, 1, 0, 0), 0],
[datetime.datetime(2021, 4, 1, 0, 0), 2],
[datetime.datetime(2021, 8, 1, 0, 0), 5],
[datetime.datetime(2021, 10, 1, 0, 0), 5]
]
result = [
# Within each group, sort, and pick out the first (oldest) list
sorted(group)[0][0]
# Group the sub-lists by the second element
for _, group in itertools.groupby(my_list, key=lambda li: li[1])
]
return result
for x in get_dates():
print(x)
输出:
[datetime.datetime(2021, 1, 1, 0, 0), 0]
[datetime.datetime(2021, 4, 1, 0, 0), 2]
[datetime.datetime(2021, 8, 1, 0, 0), 5]
我正在尝试为这个任务找到一个更优雅的解决方案:我们有一个包含日期和值对的列表列表 -> 需要与邻居值进行比较并且如果值相同 - 我们只选择最早的日期(但它只适用于近邻)。
l = [[datetime.datetime(2021, 1, 1, 0, 0), 0],
[datetime.datetime(2021, 3, 1, 0, 0), 0], # need to skipp
[datetime.datetime(2021, 4, 1, 0, 0), 2],
[datetime.datetime(2021, 8, 1, 0, 0), 0], # keep!
[datetime.datetime(2021, 10, 1, 0, 0), 5]]
预期结果:
[datetime.datetime(2021, 1, 1, 0, 0),
datetime.datetime(2021, 4, 1, 0, 0),
datetime.datetime(2021, 8, 1, 0, 0),
datetime.datetime(2021, 10, 1, 0, 0)]
请看一个例子,看看我是如何解决这个问题的。非常感谢任何关于如何优化它的想法!
def get_dates_1(): # solution 1 with reverse
l = [[datetime.datetime(2021, 1, 1, 0, 0), 0],
[datetime.datetime(2021, 3, 1, 0, 0), 0], # need to skip
[datetime.datetime(2021, 4, 1, 0, 0), 2],
[datetime.datetime(2021, 8, 1, 0, 0), 5],
[datetime.datetime(2021, 10, 1, 0, 0), 5]] # need to skip
l.reverse()
dates = []
for i in range(len(l)):
if i < len(l) - 1:
if l[i][1] != l[i + 1][1]:
dates.append(l[i][0])
else:
dates.append(l[i][0])
return list(reversed(dates))
def get_dates_2(): # solution 2 w/o reverse
l = [[datetime.datetime(2021, 1, 1, 0, 0), 0],
[datetime.datetime(2021, 3, 1, 0, 0), 0], # need to skip
[datetime.datetime(2021, 4, 1, 0, 0), 2],
[datetime.datetime(2021, 8, 1, 0, 0), 5],
[datetime.datetime(2021, 10, 1, 0, 0), 5]] # need to skip
l.sort(key=lambda x: x[0])
result = [l[0]]
for date, value in l:
if value != result[-1][1]:
result.append([date, value])
dates = [x for x, _ in result]
return dates
预计:
[datetime.datetime(2021, 1, 1, 0, 0),
datetime.datetime(2021, 4, 1, 0, 0),
datetime.datetime(2021, 8, 1, 0, 0)]
我的解决方案使用 itertools.groupyby
将列表分成子组。
import datetime
import itertools
def get_dates():
my_list = [
[datetime.datetime(2021, 3, 1, 0, 0), 0],
[datetime.datetime(2021, 1, 1, 0, 0), 0],
[datetime.datetime(2021, 4, 1, 0, 0), 2],
[datetime.datetime(2021, 8, 1, 0, 0), 5],
[datetime.datetime(2021, 10, 1, 0, 0), 5]
]
result = [
# Within each group, sort, and pick out the first (oldest) list
sorted(group)[0][0]
# Group the sub-lists by the second element
for _, group in itertools.groupby(my_list, key=lambda li: li[1])
]
return result
for x in get_dates():
print(x)
输出:
[datetime.datetime(2021, 1, 1, 0, 0), 0]
[datetime.datetime(2021, 4, 1, 0, 0), 2]
[datetime.datetime(2021, 8, 1, 0, 0), 5]