我有两个具有共同属性的模型,如果两个属性相等,我想两个组合它们,每个模型从不同的数据库中获取数据:
class User(models.Model):
matricula = models.CharField(max_length=100)
def __unicode__(self):
return self.matricula
class UserMoodle(models.Model):
matricula = models.CharField(max_length=100)
def __unicode__(self):
return self.matricula
如果我有:
lists_users = [<User: 123>, <User: 2345>,<User:567>]
lists_users_moodle = [<UserMoodle:123>, <UserMoodle:2345>, <UserMoodle:897>]
我想将它们组合起来得到这个结果:
combined_models_lists = [[<User: 123>, <UserMoodle: 123>], [<User: 2345>, <UserMoodle: 2345>], [<User: 567>, None],[None, <UserMoodle: 897>]]
提前致谢!
答案 0 :(得分:2)
一种方法是首先从这些列表(或QuerySet)创建dicts,然后迭代这些dicts的键的并集以获得所需的输出:
dict_users = {x.matricula : x for x in lists_users}
dict_moodle = {x.matricula : x for x in lists_users_moodle}
combined_models_lists = [[dict_users.get(x), dict_moodle.get(x)]
for x in set(dict_users).union(dict_moodle)]
另一种方法是迭代每个QuerySet的排序版本,然后对列表进行填充,这样我们将使用比上述方法更少的内存:
users = User.objects.all().order_by('matricula') #order by field `matricula`
moodles = UserMoodle.objects.all().order_by('matricula')
out = []
it1 = iter(users)
it2 = iter(moodles)
prev1 = next(it1)
prev2 = next(it2)
while True:
if prev1.matricula == prev2.matricula:
out.append([prev1, prev2])
try:
prev1 = next(it1)
prev2 = next(it2)
except StopIteration:
out.extend([x, None] for x in it1)
out.extend([None, x] for x in it2)
break
if prev1.matricula < prev2.matricula :
out.append([prev1, None])
try:
prev1 = next(it1)
except StopIteration:
out.append([None, prev2])
out.extend([None, x] for x in it2)
break
if prev1.matricula > prev2.matricula :
out.append([None, prev2])
try:
prev2 = next(it2)
except StopIteration:
out.extend([prev1, None])
out.extend([x, None] for x in it1)
break