微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

python – 如何改进这个多对多的Django ORM查询和模型集?

我有一个Django查询和一些Python代码,我正在尝试优化,因为1)它很丑,它不像我可以用来编写它的一些sql,2)因为数据的层次重组对我来说看起来很混乱.

所以,
1.是否可以将其改进为单个查询
2.如何将我的Python代码改进为Pythonic?

背景

这是一个照相馆系统.特定视图正在尝试显示图库中所有照片的缩略图.每张照片都是静态调整大小几次,以避免动态调整大小,我还想检索每个大小的URL和“大小类型”(例如缩略图,中等,大),以便我可以LightBox替代大小而不再访问数据库.

实体

我有5个相关的模型:

class gallery(models.Model):
    Photos = models.ManyToManyField('Photo', through = 'galleryPhoto', blank = True, null = True)

class galleryPhoto(models.Model):
    gallery = models.ForeignKey('gallery')
    Photo = models.ForeignKey('Photo')
    Order = models.PositiveIntegerField(default = 1)

class Photo(models.Model):
    GUID = models.CharField(max_length = 32)

class PhotoSize(models.Model):
    Photo = models.ForeignKey('Photo')
    PhotoSizing = models.ForeignKey('PhotoSizing')
    PhotoURL = models.CharField(max_length = 1000)

class PhotoSizing(models.Model):
    SizeName = models.CharField(max_length = 20)
    Width = models.IntegerField(default = 0, null = True, blank = True)
    Height = models.IntegerField(default = 0, null = True, blank = True)
    Type = models.CharField(max_length = 10, null = True, blank = True)

所以,粗略的想法是我希望通过galleryPhoto获取图库中的所有照片,并且对于每张照片,我想获得所有的PhotoSizes,我希望能够通过循环访问所有这些数据.字典.

sql的粗略草图可能如下所示:

Select PhotoSize.PhotoURL
From PhotoSize
Inner Join Photo On Photo.id = PhotoSize.Photo_id
Inner Join galleryPhoto On galleryPhoto.Photo_id = Photo.id
Inner Join gallery On gallery.id = galleryPhoto.gallery_id
Where gallery.id = 5
Order By galleryPhoto.Order Asc

我想将其转换为具有如下模式的列表:

(
    photo: {
        'guid': 'abcdefg',
        'sizes': {
            'Thumbnail': 'http://mysite/image1_thumb.jpg',
            'Large': 'http://mysite/image1_full.jpg',
            more sizes...
        }
    },
    more photos...
)

我目前有以下Python代码(它并不完全模仿上面的模式,但它会做一个例子).

gallery_photos = [(photo.Photo_id, photo.Order) for photo in galleryPhoto.objects.filter(gallery = gallery)]
photo_list = list(PhotoSize.objects.select_related('Photo', 'PhotoSizing').filter(Photo__id__in=[gallery_photo[0] for gallery_photo in gallery_photos]))

photos = {}
for photo in photo_list:
    order = 1
    for gallery_photo in gallery_photos:
        if gallery_photo[0] == photo.Photo.id:
            order = gallery_photo[1] //this gets the order column value

            guid = photo.Photo.GUID
            if not guid in photos:
                photos[guid] = { 'Photo': photo.Photo, 'Thumbnail': None, 'Sizes': [], 'Order': order }

            photos[guid]['Sizes'].append(photo)

    sorted_photos = sorted(photos.values(), key=operator.itemgetter('Order'))

实际问题,第1部分

所以,我的问题首先是我是否可以更好地进行多对多查询,这样我就不必对gallery_photos和photo_list进行双重查询.

实际问题,第2部分

我看看这段代码,我对它的外观并不太兴奋.我当然希望有一种更好的方法可以将列名称的分层查询集结果分组到字典中.在那儿?

解决方法:

当你有SQL查询时,使用orm很难编写 – 你可以使用postgresql视图.关于MysqL不确定.在这种情况下,您将拥有:

原始sql像:

CREATE VIEW photo_urls AS
Select
photo.id, --pseudo primary key for django mapper
gallery.id as gallery_id, 
PhotoSize.PhotoURL as photo_url
From PhotoSize
Inner Join Photo On Photo.id = PhotoSize.Photo_id
Inner Join galleryPhoto On galleryPhoto.Photo_id = Photo.id
Inner Join gallery On gallery.id = galleryPhoto.gallery_id
Order By galleryPhoto.Order Asc

Django模型如:

class PhotoUrls(models.Model):
    class Meta: 
         managed = False 
         db_table = 'photo_urls'
    gallery_id = models.IntegerField()
    photo_url = models.CharField()

ORM Queryset如:

PhotoUrls.objects.filter(gallery_id=5)

希望它会有所帮助.

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐