我的代码:
def merge_join(self, outer, outer_join_index, inner, inner_join_index):
a=list(inner)
b=list(outer)
if not a or not b:
return
inner_copy = sorted(a,key=lambda tup: tup[inner_join_index])
outer_copy = sorted(b,key=lambda tup: tup[outer_join_index])
inner_counter=0
outer_counter=0
while inner_counter < len(inner_copy) and outer_counter < len(outer_copy):
if outer_copy[outer_counter][outer_join_index]==inner_copy[inner_counter][inner_join_index]:
yield outer_copy[outer_counter]+inner_copy[inner_counter]
outer_counter+=1
elif outer_copy[outer_counter][outer_join_index]<inner_copy[inner_counter][inner_join_index]:
outer_counter+=1
else:
inner_counter+=1
外部和内部是发电机。
我为算法运行了一个给定的测试,但它返回了一个127个元素的生成器,而不是预期的214个。有人可以帮我检查我的代码中的bug可能在哪里吗?谢谢!!
答案 0 :(得分:0)
如果您想为每个outer
行选择正确的inner
行(inner
中没有重复行,如果没有匹配则跳过行,那么如果匹配,则为应该像你一样增加inner_counter
,而不是outer_counter
。
原因是否则如果多个内部行具有相同的值,则只输出其中的第一行。
如果您想要进行完全连接(从inner
和outer
为连接列的给定值生成行的所有笛卡尔积),则必须使用某些内容明确编码像
while inner_counter < len(inner_copy) and outer_counter < len(outer_copy):
key = min(inner_copy[inner_index][inner_join_index],
outer_copy[outer_index][outer_join_index])
inner_group = []
while inner_index < len(inner) and key == inner_copy[inner_index][inner_join_index]:
inner_group.append(inner_copy[inner_index])
inner_index += 1
outer_group = []
while outer_index < len(outer) and key == outer_copy[outer_index][outer_join_index]:
outer_group.append(outer_copy[outer_index])
outer_index += 1
# Here you can handle left or right join by replacing an
# empty group with a group of one empty row (None,)*len(row)
for i in inner_group:
for o in outer_group:
yield i + o