2

Web サイトへのすべてのログインを保存しておくテーブルがあります。構造は次のようになります。

TABLE users_logins

loginid INT UNSIGNED AUTO_INCREMENT PRIMARY KEY
userid INT
iplogin VARCHAR(15)
logindate datetime

ここで、同じ IP で最初にログインしたユーザーの数を取得するためのクエリが必要です。結果は次のようになります。

iplogin | numberofaccounts

ここで、'numberofaccounts' は、前に述べたように、同じ 'iplogin' で最初のログインを行ったユーザーの数です。

テーブルには約30万行あります...では、必要なものを適切なパフォーマンスで取得するにはどうすればよいですか?

ありがとう、

L.

4

2 に答える 2

0

ユーザー テーブルに最初のログイン IP の列を追加するだけです。それからそれは簡単です

select count(*), firstip 
from users 
group by firstip
于 2013-03-28T15:15:36.663 に答える
0

Add these indexes:

alter table users_logins 
  add key (iplogin, userid, logindate),
  add key (userid, logindate);

Now demonstrate that you can do the query to get the earliest login for each user by finding the login where there is no other earlier login for the same user.

This is a common solution to get the greatest/earliest entry per user or whatever.

select t1.iplogin, count(*) as numberofaccounts 
from users_logins as t1 
left outer join users_logins as t2 
  on (t1.userid=t2.userid and t1.logindate > t2.logindate) 
where t2.userid is null 
group by iplogin\G

The indexes defined above help the LEFT OUTER JOIN and the GROUP BY.

The EXPLAIN report shows that this is pretty well optimized. It makes use of indexes for both tables, and does not cause a temp table or filesort, which are frequently performance killers.

It does do an index-scan (type: index) which means it reads the entire index, but at least that's not a table-scan.

*************************** 1. row ***************************
           id: 1
  select_type: SIMPLE
        table: t1
   partitions: NULL
         type: index
possible_keys: iplogin
          key: iplogin
      key_len: 29
          ref: NULL
         rows: 1
     filtered: 100.00
        Extra: Using index
*************************** 2. row ***************************
           id: 1
  select_type: SIMPLE
        table: t2
   partitions: NULL
         type: ref
possible_keys: userid
          key: userid
      key_len: 5
          ref: test.t1.userid
         rows: 1
     filtered: 100.00
        Extra: Using where
于 2017-01-25T17:11:11.610 に答える