2013-07-02 46 views
0

我對postgres非常陌生,並且遇到了相當困難的問題,這些問題我非常需要。另外,我不是在一個合適的編輯器中工作,它是某種基於web的編輯器。請考慮一下。Postgres某種加入?

這裏我查詢:

select coalesce('user') as user_src, 
     coalesce(root_domain(hostname), hostname, 'unknown') as web_domain, 
     count (*) as nohits 
from $log 
where coalesce(root_domain(hostname), hostname, 'unknown') in 
    (select coalesce(root_domain(hostname), hostname, 'unknown') as web_domain 
      from $log 
      group by web_domain 
      limit 10 
    ) 
group by user_src, web_domain 
order by user_src, web_domain, nohits desc 

但結果不看我多麼希望他們看。 我想擁有所有用戶+他們的前10個網站。 現在我看到所有用戶和一個總共共10個網站,分爲所有用戶。 - >一些用戶然後只有0,因爲他們從來沒有去過前10名中的一個。

Thx for looking into its!

編輯:這就是我如何改變它(不工作 - 這個錯誤:錯誤:列「主機名」不存在)

select coalesce('user') as user_src, 
     coalesce(root_domain(hostname), hostname, 'unknown') as web_domain, 
     count (*) as nohits 
from 
    (select coalesce('user') as user_src, 
      coalesce(root_domain(hostname), hostname, 'unknown') as web_domain, 
      count (*) as nohits, 
      rank() over (partition by coalesce('user') order by coalesce('user'), count (*) desc) as rank 
    from $log 
    group by user_src, web_domain) w 
where rank <= 2 
order by user_src, rank 

這將工作如:(只是爲了確保「主機名」存在)

select coalesce('user') as user_src, 
     coalesce(root_domain(hostname), hostname, 'unknown') as web_domain, 
     count (*) as nohits 
from $log 
group by user_src, web_domain 
order by user_src, nohits 

回答

1

您發佈的查詢無法顯示「用戶」細分,因爲「coalesce('user')」部分是單個實體。 PostgreSQL的Window Functions之一適合你。我將演示一個使用RANK()的簡單示例,以獲取特定用戶的前N個。

begin; 

drop table if exists weblog; 
create table weblog (
"user" int, 
url  text 
); 

insert into weblog values 
(1,'http://www.1.com'), 
(1,'http://www.1.com'), 
(1,'http://www.2.com'), 
(1,'http://www.2.com'), 
(1,'http://www.3.com'), 
(1,'http://www.4.com'), 
(1,'http://www.5.com'), 
(1,'http://www.6.com'), 

(2,'http://www.2.com'), 
(2,'http://www.2.com'), 
(2,'http://www.3.com'), 
(2,'http://www.4.com'), 
(2,'http://www.4.com'), 
(2,'http://www.4.com'), 
(2,'http://www.5.com'), 
(2,'http://www.6.com'); 


select "user", 
     url, 
     hits, 
     rank 
from (select "user", 
       url, 
       count(*) as hits, 
       rank() over (partition by "user" order by count(*) desc,url) as rank 
     from weblog 
     group by "user",url) w 
where rank <= 2 
order by "user",rank; 

user |  url  | hits | rank 
------+------------------+------+------ 
    1 | http://www.1.com | 2 | 1 
    1 | http://www.2.com | 2 | 2 
    2 | http://www.4.com | 3 | 1 
    2 | http://www.2.com | 2 | 2 


rollback; 

希望對您有用。


[OP編輯答案後:]

你的外部查詢應該只從內部查詢拉動列,不重做相同的步驟。嘗試以下(從您最近的編輯)

select user_src, 
     web_domain, 
     nohits 
from 
    (select coalesce('user') as user_src, 
      coalesce(root_domain(hostname), hostname, 'unknown') as web_domain, 
      count (*) as nohits, 
      rank() over (partition by coalesce('user') order by coalesce('user'), count (*) desc) as rank 
    from $log 
    group by user_src, web_domain) w 
where rank <= 2 
order by user_src, rank 
+0

我有一個關於這個問題;那是一張臨時桌子嗎?因爲我沒有權限更改數據庫本身。 thx的信息,我會盡快測試它。 – XXInvidiaXX

+0

我上面創建的「weblog」表只是爲了演示一個真實表上的Window函數。我沒有桌子的結構或測試數據,所以我很快製作了一些測試。 – bma

+0

也許我很困惑,但我不明白你的查詢會如何減少每個用戶的域數量。 +我沒有「等級」這樣的東西。我不能在桌子上工作。它是靜態的,我可以查詢它。我通過將匹配與域相結合來「創造」排名。並把它們降下來。目標仍然是查詢所有用戶,並且只有有限數量的10個域名PER用戶 – XXInvidiaXX