4

特定の国から誰かが電話をかけた回数を時間で並べ替える必要があります。国のリストは月ごとに増えるので、たとえばブラジルを追加できます。SQLServerを使用しています。

データは次のようになります

2012-04-02 08:00:59    United States
2012-04-02 08:12:02    United States
2012-04-02 08:13:42    Canada
2012-04-02 08:13:56    United States
2012-04-02 08:14:07    Mexico
2012-04-02 08:18:09    Canada
2012-04-02 08:19:50    United States
2012-04-02 08:34:34    Mexico
etc.

データの一覧表示方法は、上位2か国別です

次のように表示したいと思います。

Date                   Country          Calls
2012-04-02 08:00:00    United States    24
2012-04-02 08:00:00    Canada           19
--hidden--
2012-04-02 08:00:00    Mexico           12

私が試したコード(機能しません):

Declare @StartDate datetime, @EndDate datetime
    set @StartDate = '20120401 00:00:00'
  set @EndDate = '20120430 23:59:59'
SELECT  DATEADD(HOUR, DATEPART(HOUR, [date]), DATEDIFF(DAY, 0, [date])) as [date],
(SELECT COUNT([country]) FROM [mytable] WHERE [date] between @StartDate and @EndDate and [country] = 'United States' ) as [United_States]
,(SELECT COUNT([country]) FROM [mytable] WHERE [date] between @StartDate and @EndDate and [country] = 'Canada' ) as [Canada]
,(SELECT COUNT([country]) FROM [mytable] WHERE [date] between @StartDate and @EndDate and [country] = 'Mexico' ) as [Canada]
FROM [mytable] 
WHERE [date] between @StartDate and @EndDate
GROUP BY DATEADD(HOUR, DATEPART(HOUR, [date]), DATEDIFF(DAY, 0, [date]))
ORDER BY [date]

ありがとうございました。

4

6 に答える 6

1

これを試して。構文エラーがあるかもしれませんが、正しい方向に進んでいると思います。

SELECT T1.Date, T1.Country, SUM(1)
FROM CallsTable T1
GROUP BY DATEADD(hh, DATEDIFF(hh,0,T1.Date),0), T1.Country
HAVING T1.Country IN (SELECT TOP 2 T2.Country
                      FROM CallsTable T2
                      WHERE DATEADD(hh, DATEDIFF(hh,0,T2.Date),0) = DATEADD(hh, DATEDIFF(hh,0,T1.Date),0)
                      GROUP BY T2.Country
                      ORDER BY SUM(1) DESC                    
                      )

説明:

DATEADD(hh, DATEDIFF(hh,0,T1.Date),0)時間でグループ化するために、分と秒を切り捨てます。

時間と国による主な選択グループ。内側の選択はフィルターであるため、指定された時間の上位2つの発信国のみが表示されます。

于 2012-04-20T22:34:49.620 に答える
1

cteと句を使用すると、over比較的簡単で読みやすくなります。

WITH CTE AS(
      SELECT DATEADD(HOUR, DATEDIFF(HOUR, 0, Date), 0)AS DateHour
    , Country
    , Count(*) OVER(Partition By Country, DATEPART(HOUR, Date))as GrpCount
    FROM @mytable
    WHERE date between @StartDate and @EndDate
)
SELECT DateHour AS Date, Country, GrpCount AS Calls
FROM CTE
GROUP BY Country, DateHour, GrpCount
ORDER BY DateHour

サンプルデータは次のとおりです。

declare @myTable table(date datetime, country varchar(20));
insert into @myTable values(convert(datetime,'2012-04-02 08:00:59',102),'United States');
insert into @myTable values(convert(datetime,'2012-04-02 08:13:42',102),'Canada');
insert into @myTable values(convert(datetime,'2012-04-02 08:13:56',102),'United States');
insert into @myTable values(convert(datetime,'2012-04-02 08:14:07',102),'Mexico');
insert into @myTable values(convert(datetime,'2012-04-02 08:18:09',102),'Canada');
insert into @myTable values(convert(datetime,'2012-04-02 08:19:50',102),'United States');
insert into @myTable values(convert(datetime,'2012-04-02 08:34:34',102),'Mexico');

Declare @StartDate datetime, @EndDate datetime;
    set @StartDate = '20120401 00:00:00';
    set @EndDate = '20120430 23:59:59';

結果:

Date                      Country           Calls
2012-04-02 08:00:00.000   Canada            2
2012-04-02 08:00:00.000   Mexico            2
2012-04-02 08:00:00.000   United States     3
于 2012-04-20T22:52:28.073 に答える
1

これはそれを行う必要があります:

Declare @StartDate datetime, 
    @EndDate datetime
    set @StartDate = '20120401 00:00:00'
    set @EndDate = '20120430 23:59:59'

;WITH
  mytablePlusHours As
(
    SELECT *,
        DATEADD(HOUR, DATEPART(HOUR, [date]), DATEDIFF(DAY, 0, [date]))     AS [dateHour]
    FROM    [mytable]    
)
, mytableHourGroups As
(
    SELECT  dateHour, 
            country,
            COUNT(*)        As [countryCount],
            ROW_NUMBER() OVER(PARTITION BY dateHour ORDER BY countryCount) 
                            As [countryRank]
    FROM        mytablePlusHours
    GROUP BY    dateHour, country
)
SELECT  
        dateHour     AS [date],
        country,
        countryCount
FROM    mytableHourGroups
WHERE   [date] between @StartDate and @EndDate
  AND   countryRank <= 2
ORDER BY [date], countryRank
于 2012-04-20T22:58:28.710 に答える
0

Darren Daviesの回答に加えて、日付と時間で解決するテーブル出力をさらに定義できます。

SELECT 
  DATEADD(dd, 0, DATEDIFF(dd, 0, [Date])) as Date, 
  DATEPART(HOUR, [Date]) as Hour, 
  Country, 
  SUM(Calls)
FROM YourTable
GROUP BY 
  DATEADD(dd, 0, DATEDIFF(dd, 0, [Date])),
  DATEPART(HOUR, [Date]), 
  Country
于 2012-04-20T22:35:03.653 に答える
0

未テスト:

SELECT date(yourdate) as mday, 
       datepart(hour, yourdate) as Yourhour, 
       country, 
       count(*) as calls, 
       ROW_NUMBER() OVER(PARTITION BY date(YourDate) & "-" & Datepart(hour,YourDate) & ORDER BY count(*) DESC) myCount
FROM yourTableName
GROUP BY date(yourdate), datepart(hour, yourdate)
having myCount <3
Order by count(*), mday, yourhour

どういうわけかRow_NUMBER()Over(partiion By ...はあなたが望むものを手に入れるようです」が、私はそれをテストできません。使用についてはMSFT ARTICLEを参照し、なぜそれがあなたの後にあると思うのか。

基本的に、曜日と時間に異なるパーティションを作成し、そのパーティションセット内の呼び出しの数で並べ替え、レコード/カウントごとに1から1ずつ増加する番号を割り当てます。次に、そのレコード/カウントを各日/時間グループの上位2つに制限します。

于 2012-04-20T22:38:03.893 に答える
0

最も簡単な解決策は、2 つのステップにあると思います。

まず、日時を偶数時間に変換する必要があります。あるテーブルから別のテーブルにデータをコピーするか、ビューを介してデータをコピーするか、テーブルに計算フィールドを追加してください。

次に、次のようなことをします

select date time, country, count(*) calls
from mytable
group by date, country

それが「count(*)」であるかどうかはわかりません-誰かが私を修正してください。

于 2012-04-20T22:20:08.697 に答える