Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/77.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
根据PostgreSQL中的频率获取单词的最新排名_Sql_Postgresql_Count_Greatest N Per Group_Lateral Join - Fatal编程技术网

根据PostgreSQL中的频率获取单词的最新排名

根据PostgreSQL中的频率获取单词的最新排名,sql,postgresql,count,greatest-n-per-group,lateral-join,Sql,Postgresql,Count,Greatest N Per Group,Lateral Join,我有一个存储twitter数据的数据库: Create Table tweet( ID BIGINT UNIQUE, user_ID BIGINT, created_at TIMESTAMPTZ, tweet TEXT; 我正在尝试编写一个查询,通过tweet中所有行的单词来获取每个单词的频率,并返回前十个最频繁的单词以及单词在每个日期的排名 例如: ("word1&quo

我有一个存储twitter数据的数据库:

        Create Table tweet(
            ID BIGINT UNIQUE,
            user_ID BIGINT,
            created_at TIMESTAMPTZ,
            tweet TEXT;
我正在尝试编写一个查询,通过tweet中所有行的单词来获取每个单词的频率,并返回前十个最频繁的单词以及单词在每个日期的排名

例如:

("word1":[1,20,22,23,24,25,26,27,28,29,30,29,28,27,26,25,26,27,28,29,30,29,28,29,28,27,28,29,30,30,...],
'word2' [...])
我当前的查询得到了前十个单词,但我在获取这些单词每天的排名时遇到了一些困难

当前查询:

    SELECT word, count(*)
    FROM (
        SELECT regexp_split_to_table(
            regexp_replace(tweet_clean, '\y(rt|co|https|amp|f)\y', '', 'g'), '\s+')
        AS word
    FROM tweet
    ) t
    GROUP BY word
    ORDER BY count(*) DESC
    LIMIT 10;
返回:

[('vaccine', 286669),
 ('covid', 213857),
 ('yum', 141345),
 ('pfizer', 39532),
 ('people', 28960),
 ('beer', 27117),
 ('say', 24569),
 ('virus', 23682),
 ('want', 21988),
 ('foo', 19823)]
如果您希望每天获得前10名,您可以:

select *
from (
    select date_trunc('day', created_at) as created_day, word, count(*) as cnt,
        rank() over(partition by date_trunc('day', created_at) order by count(*) desc) rn
    from tweet t
    cross join lateral regexp_split_to_table(
        regexp_replace(tweet_clean, '\y(rt|co|https|amp|f)\y', '', 'g'),
        '\s+'
    ) w(word)
    group by created_day, word
) t
where rn <= 10
order by created_day, rn desc

如果我理解正确,您需要10行最常用的单词。然后你需要一组频率。假设每天都使用每个单词,则应该这样做:

select wd.word,
       array_agg(day_rank) over (order by created_day) as ranks
from (select date_trunc('day', t.created_at) as created_day, w.word,
             sum(count(*)) as total_cnt,
             rank() over(partition by date_trunc('day', created_at) order by count(*) desc) as day_rank
      from tweet t cross join lateral
           regexp_split_to_table(regexp_replace(tweet_clean, '\y(rt|co|https|amp|f)\y', '', 'g'
                                               ), '\s+'
                                ) w(word)
      group by created_day, word
     ) wd
order by total_cnt desc
limit 10;
这里的挑战是阵列可能具有不同的长度。在Postgres中,你可以添加额外的值,但不清楚排名应该放在哪里

问题是排名是每天的。所以,考虑两天,一个有100个单词,一个有10个单词。在第一种情况下,排名10是一个非常高的排名。第二名的排名是十分低的


我建议您考虑一下这个问题,如果您需要帮助解决它,可以问一个新问题。

您可以使用rank或dense_rank获得排名。谢谢您的回答。我在运行您的查询时收到一个错误:psycopg2.errors.SyntaxError:第3行或其附近的语法错误:数组\u aggday \u按创建的顺序排列\u day as rank…@mehsheenman。哎呀,缺少一些括号。