1

次の2つのテーブルがあります。

TableOne
-RawDataId int(pk)-TimeStamp
DateTime
-BuildingID int

TableTwo
-RawDataId int(pk / fk)
-MeterId int(pk)
-実数値

MeterIdは一意ではなく、複数回繰り返されます(ただし、常に同じ数になります)。2つのテーブルは問題なく結合されます。上位15行を選択し、タイムスタンプで注文して、各メーターの最新の値を取得できます(合計15、それぞれにタイムスタンプが付いています)。ただし、以前の時間(正確に1440分と1439分前)から各メーターの値を取得する必要もあります-それが理にかなっている場合。

したがって、クエリを実行した後、TableOneとTableTwoの列を含むテーブルが必要ですが、ValueBとValueCの列が2つ追加されています(Bは1440分前の値、Cは1439前の値です)。私は彼の一日中そして昨夜のほとんどで遊んでいました、そして私はゆっくりと陰謀を失っています。

どんな助けでもいただければ幸いです。のぞき見ありがとう。

- - アップデート

以下に、いくつかのサンプルデータとともに実際のテーブルスキーマを含めました。

CREATE TABLE [dbo].[TableOne](
[RawDataId] [bigint] IDENTITY(1,1) NOT NULL,
[TimeStamp] [datetime] NOT NULL,
[BuildingId] [int] NULL,
CONSTRAINT [TableOne_PK] PRIMARY KEY CLUSTERED 

CREATE TABLE [dbo].[TableTwo](
[MeterId] [bigint] NOT NULL,
[RawDataId] [bigint] NOT NULL,
[Value] [real] NULL,
 CONSTRAINT [TableTwo_PK] PRIMARY KEY CLUSTERED 

TableOneの最後の30レコードのサンプルデータ:

RawDataId, TimeStamp, BuildingId
21677   2012-05-16 00:03:00.000 1
21678   2012-05-16 00:03:00.000 1
21679   2012-05-16 00:03:00.000 1
21680   2012-05-16 00:03:00.000 1
21681   2012-05-16 00:03:00.000 1
21682   2012-05-16 00:03:00.000 1
21683   2012-05-16 00:03:00.000 1
21684   2012-05-16 00:03:00.000 1
21685   2012-05-16 00:03:00.000 1
21686   2012-05-16 00:03:00.000 1
21687   2012-05-16 00:03:00.000 1
21688   2012-05-16 00:03:00.000 1
21689   2012-05-16 00:03:00.000 1
21690   2012-05-16 00:03:00.000 1
21691   2012-05-16 00:03:00.000 1
21662   2012-05-16 00:02:00.000 1
21663   2012-05-16 00:02:00.000 1
21664   2012-05-16 00:02:00.000 1
21665   2012-05-16 00:02:00.000 1
21666   2012-05-16 00:02:00.000 1
21667   2012-05-16 00:02:00.000 1
21668   2012-05-16 00:02:00.000 1
21669   2012-05-16 00:02:00.000 1
21670   2012-05-16 00:02:00.000 1
21671   2012-05-16 00:02:00.000 1
21672   2012-05-16 00:02:00.000 1
21673   2012-05-16 00:02:00.000 1
21674   2012-05-16 00:02:00.000 1
21675   2012-05-16 00:02:00.000 1
21676   2012-05-16 00:02:00.000 1

TableTwoのサンプル:

MeterId, RawDataId, Value
15  21691   7722613
14  21690   908944
13  21689   4982947
12  21688   3821899
11  21687   6
10  21686   0
9   21685   0
8   21684   5761656
7   21683   4240048
6   21682   1541372
5   21681   283223
4   21680   1.298603E+07
3   21679   388137
2   21678   876121
1   21677   0
15  21676   7722615
14  21675   908944
13  21674   4982947
12  21673   3821899
11  21672   5
10  21671   0
9   21670   0
8   21669   5761656
7   21668   4240052
6   21667   1541372
5   21666   283223
4   21665   1.298604E+07
3   21664   388137
2   21663   876122
1   21662   0

メーターの読み取り値は、1ごとにテーブルに書き込まれます(したがって、タイムスタンプ)。上位15レコード(最新の値を取得するためにTimeStampでソート)を選択するときは、1440分前と1439分前(最新のTimeStampと比較して)のメーターの値も取得する必要があります。これがより明確になることを願っています。

これまでのところ、私のSQLクエリは次のようになっています。

SELECT TOP 15 * FROM (Select TableOne.[RawDataId], 
[TimeStamp], BuildingId, MeterId, `enter code here`Value 
FROM [TableOne]
INNER JOIN TableTwo ON
TableOne = TableTwo) as PS
ORDER BY [TimeStamp];

クエリは次のようになりますが、TimeStampと比較して、1440分前と1439分前のメーターの値を持つ追加の2つの列が必要です。

RawDataId, TimeStamp, BuildingId, MeterId, Value
21677   2012-05-16 00:03:00.000 1   1   0
21678   2012-05-16 00:03:00.000 1   2   876121
21679   2012-05-16 00:03:00.000 1   3   388137
21680   2012-05-16 00:03:00.000 1   4   1.298603E+07
21681   2012-05-16 00:03:00.000 1   5   283223
21682   2012-05-16 00:03:00.000 1   6   1541372
21683   2012-05-16 00:03:00.000 1   7   4240048
21684   2012-05-16 00:03:00.000 1   8   5761656
21685   2012-05-16 00:03:00.000 1   9   0
21686   2012-05-16 00:03:00.000 1   10  0
21687   2012-05-16 00:03:00.000 1   11  6
21688   2012-05-16 00:03:00.000 1   12  3821899
21689   2012-05-16 00:03:00.000 1   13  4982947
21690   2012-05-16 00:03:00.000 1   14  908944
21691   2012-05-16 00:03:00.000 1   15  7722613
4

3 に答える 3

1

データ(そしておそらくクエリ)のサンプルを見なければ、問題を理解するのは本当に難しいです。私が正しく理解していれば、これはうまくいくはずです:

SELECT
(
SELECT TOP 1 Value
FROM TableOne t1 join TableTwo t2 ON t1.RawDataId = t2.RawDataId
WHERE t1.RawDataId IN (
SELECT RawDataId FROM TableTwo WHERE MeterId = tbl.MeterId
) and TimeStamp = DATEADD(mi, -1440, tbl.TimeStamp)
) as ValueB,
(
SELECT TOP 1 Value
FROM TableOne t1 join TableTwo t2 ON t1.RawDataId = t2.RawDataId
WHERE t1.RawDataId IN (
SELECT RawDataId FROM TableTwo WHERE MeterId = tbl.MeterId
) and TimeStamp = DATEADD(mi, -1439, tbl.TimeStamp)
) as ValueC
FROM TableTwo tbl
于 2012-05-17T14:56:43.847 に答える
1

常に1440分前と1439分前の値を設定する場合は、次のように機能する可能性があります。

SELECT TOP 15 
      TableOne.BuildingID
    , TableOne.RawDataID
    , TableOne.TimeStamp
    , TableTwo.MeterID
    , TableTwo.Value
    , TableTwo1439.Value AS ValueB
    , TableTwo1440.Value AS ValueC
FROM TableOne
JOIN TableTwo ON TableOne.RawDataID=TableTwo.RawDataID
JOIN TableTwo TableTwo1439 ON TableTwo.MeterID=TableTwo1439.MeterID
JOIN TableOne TableOne1439 ON TableTwo1439.RawDataID=TableOne1439.RawDataID AND TableOne.TimeStamp=DATEADD(MINUTE,-1439,TableOne1439.TimeStamp)
JOIN TableTwo TableTwo1440 ON TableTwo.MeterID=TableTwo1440.MeterID
JOIN TableOne TableOne1440 ON TableTwo1440.RawDataID=TableOne1440.RawDataID AND TableOne.TimeStamp=DATEADD(MINUTE,-1440,TableOne1440.TimeStamp)
ORDER BY TableOne.Timestamp DESC

それ以外の場合でも、同じアプローチを使用できますが、代わりに外部結合を使用するように調整する必要がある場合があります...

于 2012-05-17T15:01:12.603 に答える
0

SQL Server 2005以降のバージョンを使用している場合は、次のような方法を試すことができます。

WITH data AS (
  SELECT
    t1.RawDataId,
    t1.TimeStamp,
    t1.BuildingId,
    t2.MeterId,
    t2.Value,
    x.Diff AS TimeStampId
  FROM (SELECT BuildingId, MAX(TimeStamp) AS TimeStamp FROM TableOne GROUP BY BuildingId) t
    CROSS JOIN (SELECT 0 UNION ALL SELECT 1440 UNION ALL SELECT 1439) x (Diff)
    INNER JOIN TableOne t1 ON t.BuildingId = t1.BuildingId
                          AND t1.TimeStamp = DATEADD(MINUTE, -x.Diff, t.TimeStamp)
    INNER JOIN TableTwo t2 ON t2.RawDataId = t1.RawDataId
)
SELECT
  RawDataId,
  TimeStamp,
  BuildingId,
  MeterId,
  Value           = [0],
  Value1440MinAgo = [1440],
  Value1439MinAgo = [1439]
FROM data
PIVOT (
  MAX(Value) FOR TimeStampId IN ([0], [1440], [1439])
) p

つまり、ここでは、さまざまなBuildingIdを考慮したいと想定しています。これは、その列が出力に存在するためです。特定のものだけが必要な場合は、次のように副選択を書き直すことができますt

(SELECT TOP 1 * FROM TableOne WHERE BuildingId = @Id ORDER BY TimeStamp DESC) t
于 2012-05-18T07:49:31.400 に答える