0

有人可以向我提出有关如何解决以下问题的想法:

我的数据库中有图片、视频和标签。标签可以与图片和视频相关联。我必须查询数据库以获取在 7 天或更早之前修改的标签 ID 和计数,并按它们与图片和视频资产的关联计数对它们进行排序。

所以这个想法是,最后我可以输出过去 7 天内与图片或视频关联最多的标签。我用我拥有的字段写下了数据库结构

VIDEO
    ID

PICTURE
    ID

PICTURE_ATTRMAPPING
    CS_OWNERID  (ID of picture)
    CS_ATTRID  ( will store ID of the tag attribute (picture_tag or video_tag))
    ASSETVALUE ( will store ID OF THE associated tag)

VIDEO_ATTRMAPPING
    CS_OWNERID  (ID of video)
    CS_ATTRID  ( will store ID of the tag attribute (picture_tag or video_tag))
    ASSETVALUE ( will store ID OF THE associated tag)

TAG
    ID
    UPDATEDATE

ATTRIBUTES (picture_tag attribute ID is stored here)
    ID
    NAME

所以我们可以看到标签、视频、图片和属性存储在单独的表中。如果 VIDEO/PICTURE_ATTRMAPPING 表在 CS_ATTRID 列中有带有视频或图片标签属性 id 的记录,在 ASSETVALUE 列中有标签的 id,我们可以判断该标签被视频或图片引用(换句话说,视频/图片具有标签关联)。

我假设它将是带有子查询的查询,所以我开始在子任务中打破这个任务并弄清楚如何获取所需的所有信息。

我肯定要获取视频和图片对象的标签属性的 ID:

SELECT id FROM ATTRIBUTES WHERE NAME = 'picture_tag' OR NAME = 'video_tag'

还有一个示例,说明如何查询已有 n 天的标签:

SELECT id FROM TAG WHERE updateddate BETWEEN TO_DATE('2013-08-20 00:00:00', 'yyyy-mm-dd hh24:mi:ss') AND CURRENT_DATE

这可能并不像看起来那么复杂,但是,我不确定整个查询应该是什么样子以及从什么开始。有人可以提出想法或样品吗?

我正在使用 oracle,但也熟悉 mysql,因此来自任何 DBMS 的样本都会很棒。让我知道我是否足够清楚。

4

2 回答 2

1

最近 7 天更新的标签可以写成:

select id from tags where updatedate >= sysdate - 7

从你所说的 ATTRIBUTES 表中只有两个值;所以你可以忽略它。即使它有更多的表 PICTURE_ATTRMAPPING 和 VIDEO_ATTRMAPPING 确保在您加入它们时强制执行这些属性,所以这也无关紧要。

如果您希望标签与图片或视频相关联,您只需要强制它存在于 *_ARRTMAPPING 表之一中:

select *
  from tags t
  left outer join picture_attrmappings pa
    on t.id = pa.assetvalue
  left outer join video_attrmappings va
    on t.id = va.assetvalue
 where t.updatedate >= sysdate - 7
   and ( pa.assetvalue is not null
         or va.assetvalue is not null
         )

然后,您需要修改最多的标签 ID;所以你需要按计数排序:

select t.id
  from tags t
  left outer join picture_attrmappings pa
    on t.id = pa.assetvalue
  left outer join video_attrmappings va
    on t.id = va.assetvalue
 where t.updatedate >= sysdate - 7
   and ( pa.assetvalue is not null
         or va.assetvalue is not null
         )
 group by t.id
 order by count(*) desc

稍微不同的是,这是一个非常奇怪的模式(假设你什么都没有遗漏)。我希望 PICTURE_ATTRMAPPINGS 是 TAGS 和 PICTURE 之间的连接表。TAGS 表应该存储一个唯一的标签列表,但这似乎不是它的作用。然后 UPDATEDATE 应该在 PICTURE_ARRTMAPPINGS 中,这样您就可以知道每个标签的最后更新时间,或者在 PICTURE 中,这样您就可以知道所有标签的最后更新时间(或两者都更新)。

我怀疑你错过了一些模式,但我看不到使用图片或视频的方法,你所提供的。

于 2013-08-26T11:36:55.983 回答
0

分配给图片的所有标签 ID:

SELECT ASSETVALUE  
            FROM PICTURE_ATTRMAPPING 
                 JOIN ATTRIBUTES 
                 ON (      ATTRIBUTES.ID = PICTURE_ATTRMAPPING.CS_ATTRID 
                      AND  ATTRIBUTES.NAME = 'picture_tag'
                    ) 

分配给视频的所有标签 ID:

    SELECT ASSETVALUE  
    FROM   VIDEO_ATTRMAPPING 
           JOIN ATTRIBUTES 
           ON (      ATTRIBUTES.ID = PICTURE_ATTRMAPPING.CS_ATTRID 
                AND  ATTRIBUTES.NAME = 'video_tag'
              )

使用 OUTER JOIN 计算被标记的图片和视频

SELECT 
  TAG.ID
, SUM(CASE WHEN PT.ASSETVALUE is not NULL THEN 1 ELSE 0 END) as tagged_picture_number
, SUM(CASE WHEN VT.ASSETVALUE is not NULL THEN 1 ELSE 0 END) as tagged_vieos_number
  FROM 
    TAG
    LEFT OUTER JOIN 
      (
        SELECT ASSETVALUE  
        FROM PICTURE_ATTRMAPPING 
             JOIN ATTRIBUTES 
             ON ( ATTRIBUTES.ID = PICTURE_ATTRMAPPING.CS_ATTRID AND  ATTRIBUTES.NAME = 'picture_tag') 
      ) PT
      ON ( PT.ASSETVALUE = TAG.ID)
    LEFT OUTER JOIN 
      (
        SELECT ASSETVALUE  
        FROM   VIDEO_ATTRMAPPING 
               JOIN ATTRIBUTES 
               ON ( ATTRIBUTES.ID = PICTURE_ATTRMAPPING.CS_ATTRID AND  ATTRIBUTES.NAME = 'video_tag') 
      ) VT
      ON ( PT.ASSETVALUE = TAG.ID)
WHERE
    TAG.UPDATEDATE <= TRUNC(SYSDATE, 'DD') - 7
group by TAG.ID
order by tagged_picture_number + tagged_vieos_number DESC
;
于 2013-08-26T11:44:19.200 回答