|
| MySQL 4,1 og "avegaging" Fra : Lars L. Christensen |
Dato : 23-01-06 23:33 |
|
Hejsa
Jeg har en udfordring, som jeg ikke helt lige ved hvordan jeg skal klare.
Jeg har en tabel t1, som indeholder dtime og counter. dtime er en
timestamp i 5 minutters intervaller og counter er en counter.
I tabellen har jeg en pæn mængde data (1 mio records). Jeg ønsker at
trække data ud, således at jeg f.eks. kun har 300 records, men af disse
300 records skal de være averages af f.eks. 900 records, således at for
hver 3 records skal der tages en average og denne average skal så bruges.
Jeg håber det giver lidt mening...
Eksempel
t1.dtime t1.counter
2000300 1
2000600 2
2000900 3
2001200 500
2001500 1000
2001800 1250
Disse infos skal give et output i stil med:
t1.dtime t1.counter
2000900 2
1001800 916,67
Håber der er nogen der har en god ide...
| |
Michael Zedeler (24-01-2006)
| Kommentar Fra : Michael Zedeler |
Dato : 24-01-06 00:25 |
|
Lars L. Christensen wrote:
> Jeg ønsker at
> trække data ud, således at jeg f.eks. kun har 300 records, men af disse
> 300 records skal de være averages af f.eks. 900 records, således at for
> hver 3 records skal der tages en average og denne average skal så bruges.
>
> Eksempel
>
> t1.dtime t1.counter
> 2000300 1
> 2000600 2
> 2000900 3
> 2001200 500
> 2001500 1000
> 2001800 1250
>
> Disse infos skal give et output i stil med:
>
> t1.dtime t1.counter
> 2000900 2
> 1001800 916,67
Hvis feltet dtime altid stiger med 300 for hver ny række, kan det klares
med noget i stil med:
SELECT INT((dtime - 2000000)/900+1)*900 AS rounded_dtime, AVG(counter)
FROM t1
GROUP BY rounded_dtime
(Ikke testet.)
Mvh. Michael.
--
Which is more dangerous? TV guided missiles or TV guided families?
Visit my home page at http://michael.zedeler.dk/
Get my vcard at http://michael.zedeler.dk/vcard.vcf
| |
Lars L. Christensen (25-01-2006)
| Kommentar Fra : Lars L. Christensen |
Dato : 25-01-06 20:27 |
|
Michael Zedeler <michael@zedeler.dk> wrote in
news:qBdBf.5326$Cl2.130841@news000.worldonline.dk:
> Lars L. Christensen wrote:
>> Jeg ønsker at
>> trække data ud, således at jeg f.eks. kun har 300 records, men af
>> disse 300 records skal de være averages af f.eks. 900 records,
>> således at for hver 3 records skal der tages en average og denne
>> average skal så bruges.
>>
>> Eksempel
>>
>> t1.dtime t1.counter
>> 2000300 1
>> 2000600 2
>> 2000900 3
>> 2001200 500
>> 2001500 1000
>> 2001800 1250
>>
>> Disse infos skal give et output i stil med:
>>
>> t1.dtime t1.counter
>> 2000900 2
>> 1001800 916,67
>
> Hvis feltet dtime altid stiger med 300 for hver ny række, kan det
> klares med noget i stil med:
>
> SELECT INT((dtime - 2000000)/900+1)*900 AS rounded_dtime, AVG(counter)
> FROM t1
> GROUP BY rounded_dtime
>
> (Ikke testet.)
>
> Mvh. Michael.
Desværre er det ikke altid 300, der er step-size på min dtime. Den kan
variere fra 300 og op til 360. Der er derfor 3 entries = 1 output, 3
entries = 1 output osv.
mvh
Lars
| |
Michael Zedeler (25-01-2006)
| Kommentar Fra : Michael Zedeler |
Dato : 25-01-06 21:07 |
|
Lars L. Christensen wrote:
> Michael Zedeler <michael@zedeler.dk> wrote in
> news:qBdBf.5326$Cl2.130841@news000.worldonline.dk:
>
>
>>Lars L. Christensen wrote:
>>
>>>Jeg ønsker at
>>>trække data ud, således at jeg f.eks. kun har 300 records, men af
>>>disse 300 records skal de være averages af f.eks. 900 records,
>>>således at for hver 3 records skal der tages en average og denne
>>>average skal så bruges.
>>>
>>>Eksempel
>>>
>>>t1.dtime t1.counter
>>>2000300 1
>>>2000600 2
>>>2000900 3
>>>2001200 500
>>>2001500 1000
>>>2001800 1250
>>>
>>>Disse infos skal give et output i stil med:
>>>
>>>t1.dtime t1.counter
>>>2000900 2
>>>1001800 916,67
>>
>>Hvis feltet dtime altid stiger med 300 for hver ny række, kan det
>>klares med noget i stil med:
>>
>>SELECT INT((dtime - 2000000)/900+1)*900 AS rounded_dtime, AVG(counter)
>>FROM t1
>>GROUP BY rounded_dtime
>>
>>(Ikke testet.)
>
> Desværre er det ikke altid 300, der er step-size på min dtime. Den kan
> variere fra 300 og op til 360. Der er derfor 3 entries = 1 output, 3
> entries = 1 output osv.
Så har jeg ikke andre idéer, end at nummerere rækkerne fortløbende (i
feltet row_num)og bruge denne her:
SELECT INT(row_num/3) AS row_group, AVG(counter)
FROM t1
GROUP BY row_group
Det er muligt at man kan kan nummerere ved at bruge en eller anden form
for subquery, men det kan jeg ikke lige overskue. Desuden vil det være
mest optimalt at smide numrene på en gang for alle, hvis du regner med
at køre din forespørgsel flere gange. Desuden giver det mulighed for at
vælge at slå flere end tre rækker sammen i nogle specielle tilfælde (det
ved jeg ikke om du kan bruge?).
Mvh. Michael.
--
Which is more dangerous? TV guided missiles or TV guided families?
Visit my home page at http://michael.zedeler.dk/
Get my vcard at http://michael.zedeler.dk/vcard.vcf
| |
Lars L. Christensen (26-01-2006)
| Kommentar Fra : Lars L. Christensen |
Dato : 26-01-06 16:34 |
|
>>
>> Desværre er det ikke altid 300, der er step-size på min dtime. Den kan
>> variere fra 300 og op til 360. Der er derfor 3 entries = 1 output, 3
>> entries = 1 output osv.
>
> Så har jeg ikke andre idéer, end at nummerere rækkerne fortløbende (i
> feltet row_num)og bruge denne her:
>
> SELECT INT(row_num/3) AS row_group, AVG(counter)
> FROM t1
> GROUP BY row_group
>
Jeg har gjort det nu, at jeg har "kopieret" de relevante data over i en
temporær tabel og nummeret dem fortløbende. Dermed har jeg nu kun de data
jeg skal bruge og de er nummeret fortløbende.
Jeg synes ikke lige dine forslag lige vil.
Flere ideer?
mvh
Lars
| |
Michael Zedeler (26-01-2006)
| Kommentar Fra : Michael Zedeler |
Dato : 26-01-06 19:08 |
|
Lars L. Christensen wrote:
>>>Desværre er det ikke altid 300, der er step-size på min dtime. Den kan
>>>variere fra 300 og op til 360. Der er derfor 3 entries = 1 output, 3
>>>entries = 1 output osv.
>>
>>Så har jeg ikke andre idéer, end at nummerere rækkerne fortløbende (i
>>feltet row_num)og bruge denne her:
>>
>>SELECT INT(row_num/3) AS row_group, AVG(counter)
>>FROM t1
>>GROUP BY row_group
>
> Jeg har gjort det nu, at jeg har "kopieret" de relevante data over i en
> temporær tabel og nummeret dem fortløbende. Dermed har jeg nu kun de data
> jeg skal bruge og de er nummeret fortløbende.
>
> Jeg synes ikke lige dine forslag lige vil.
Hvad vil det sige at de ikke "lige vil"? Hvis du har puttet fortløbende
numre på dem, bør det virke. Hvad for fejl eller resultater får du?
Mvh. Michael.
--
Which is more dangerous? TV guided missiles or TV guided families?
Visit my home page at http://michael.zedeler.dk/
Get my vcard at http://michael.zedeler.dk/vcard.vcf
| |
Lars L. Christensen (27-01-2006)
| Kommentar Fra : Lars L. Christensen |
Dato : 27-01-06 21:49 |
|
Michael Zedeler <michael@zedeler.dk> wrote in
news:ye8Cf.5547$Cl2.132299@news000.worldonline.dk:
> Lars L. Christensen wrote:
>>>>Desværre er det ikke altid 300, der er step-size på min dtime. Den
>>>>kan variere fra 300 og op til 360. Der er derfor 3 entries = 1
>>>>output, 3 entries = 1 output osv.
>>>
>>>Så har jeg ikke andre idéer, end at nummerere rækkerne fortløbende (i
>>>feltet row_num)og bruge denne her:
>>>
>>>SELECT INT(row_num/3) AS row_group, AVG(counter)
>>>FROM t1
>>>GROUP BY row_group
>>
>> Jeg har gjort det nu, at jeg har "kopieret" de relevante data over i
>> en temporær tabel og nummeret dem fortløbende. Dermed har jeg nu kun
>> de data jeg skal bruge og de er nummeret fortløbende.
>>
>> Jeg synes ikke lige dine forslag lige vil.
>
> Hvad vil det sige at de ikke "lige vil"? Hvis du har puttet
> fortløbende numre på dem, bør det virke. Hvad for fejl eller
> resultater får du?
>
> Mvh. Michael.
mysql> select int(number/6) as row_grp, avg(counter) from temp group by
row_grp;
ERROR 1064 (42000): You have an error in your SQL syntax; check the
manual that corresponds to your MySQL server version for the right syntax
to use near 'int(number/6) as row_grp, avg(counter) from temp group by
row_grp' at line 1
Håber det giver en ide...
mvh
Lars
| |
Michael Zedeler (27-01-2006)
| Kommentar Fra : Michael Zedeler |
Dato : 27-01-06 22:41 |
|
Lars L. Christensen wrote:
> Michael Zedeler <michael@zedeler.dk> wrote in
> news:ye8Cf.5547$Cl2.132299@news000.worldonline.dk:
>
>
>>Lars L. Christensen wrote:
>>
>>>>>Desværre er det ikke altid 300, der er step-size på min dtime. Den
>>>>>kan variere fra 300 og op til 360. Der er derfor 3 entries = 1
>>>>>output, 3 entries = 1 output osv.
>>>>
>>>>Så har jeg ikke andre idéer, end at nummerere rækkerne fortløbende (i
>>>>feltet row_num)og bruge denne her:
>>>>
>>>>SELECT INT(row_num/3) AS row_group, AVG(counter)
>>>
>>>>FROM t1
>>>
>>>>GROUP BY row_group
>>>
>>>Jeg har gjort det nu, at jeg har "kopieret" de relevante data over i
>>>en temporær tabel og nummeret dem fortløbende. Dermed har jeg nu kun
>>>de data jeg skal bruge og de er nummeret fortløbende.
>>>
>>>Jeg synes ikke lige dine forslag lige vil.
>>
>>Hvad vil det sige at de ikke "lige vil"? Hvis du har puttet
>>fortløbende numre på dem, bør det virke. Hvad for fejl eller
>>resultater får du?
>
> mysql> select int(number/6) as row_grp, avg(counter) from temp group by
> row_grp;
> ERROR 1064 (42000): You have an error in your SQL syntax; check the
> manual that corresponds to your MySQL server version for the right syntax
> to use near 'int(number/6) as row_grp, avg(counter) from temp group by
> row_grp' at line 1
>
> Håber det giver en ide...
Ja. Det gør det da. "number" er et reserveret ord. I mit eksempel kalder
jeg det også for noget andet.
Mvh. Michael.
--
Which is more dangerous? TV guided missiles or TV guided families?
Visit my home page at http://michael.zedeler.dk/
Get my vcard at http://michael.zedeler.dk/vcard.vcf
| |
Lars L. Christensen (27-01-2006)
| Kommentar Fra : Lars L. Christensen |
Dato : 27-01-06 23:12 |
|
Michael Zedeler <michael@zedeler.dk> wrote in
news:MrwCf.5607$Cl2.132451@news000.worldonline.dk:
> Lars L. Christensen wrote:
>> Michael Zedeler <michael@zedeler.dk> wrote in
>> news:ye8Cf.5547$Cl2.132299@news000.worldonline.dk:
>>
>>
>>>Lars L. Christensen wrote:
>>>
>>>>>>Desværre er det ikke altid 300, der er step-size på min dtime. Den
>>>>>>kan variere fra 300 og op til 360. Der er derfor 3 entries = 1
>>>>>>output, 3 entries = 1 output osv.
>>>>>
>>>>>Så har jeg ikke andre idéer, end at nummerere rækkerne fortløbende
>>>>>(i feltet row_num)og bruge denne her:
>>>>>
>>>>>SELECT INT(row_num/3) AS row_group, AVG(counter)
>>>>
>>>>>FROM t1
>>>>
>>>>>GROUP BY row_group
>>>>
>>>>Jeg har gjort det nu, at jeg har "kopieret" de relevante data over i
>>>>en temporær tabel og nummeret dem fortløbende. Dermed har jeg nu kun
>>>>de data jeg skal bruge og de er nummeret fortløbende.
>>>>
>>>>Jeg synes ikke lige dine forslag lige vil.
>>>
>>>Hvad vil det sige at de ikke "lige vil"? Hvis du har puttet
>>>fortløbende numre på dem, bør det virke. Hvad for fejl eller
>>>resultater får du?
>>
>> mysql> select int(number/6) as row_grp, avg(counter) from temp group
>> by row_grp;
>> ERROR 1064 (42000): You have an error in your SQL syntax; check the
>> manual that corresponds to your MySQL server version for the right
>> syntax to use near 'int(number/6) as row_grp, avg(counter) from temp
>> group by row_grp' at line 1
>>
>> Håber det giver en ide...
>
> Ja. Det gør det da. "number" er et reserveret ord. I mit eksempel
> kalder jeg det også for noget andet.
>
> Mvh. Michael.
Ok, det skal åbenbare bare ikke lige lykkes for mig i dag med den her
query...
Følgende output:
mysql> create temporary table temp (row_num int not null auto_increment,
counter bigint(20), primary key(row_num)) type = heap;
Query OK, 0 rows affected, 1 warning (0.00 sec)
mysql> insert into temp (counter) SELECT (i.counter/300)*8 FROM
IntInOctets i where i.dtime < timestamp("2006-01-27 21:31:53") and
i.dtime > timestamp("2006-01-20 21:31:53") and i.id = 20105 order by
dtime;
Query OK, 1452 rows affected (0.34 sec)
Records: 1452 Duplicates: 0 Warnings: 0
mysql> select int(row_num/6) as row_grp, avg(counter) from temp group by
row_grp;
ERROR 1064 (42000): You have an error in your SQL syntax; check the
manual that corresponds to your MySQL server version for the right syntax
to use near 'int(row_num/6) as row_grp, avg(counter) from temp group by
row_grp' at line 1
mysql> select * from temp limit 10;
+---------+-----------+
| row_num | counter |
+---------+-----------+
| 1 | 110319051 |
| 2 | 22602889 |
| 3 | 41405755 |
| 4 | 21054075 |
| 5 | 22419886 |
| 6 | 21286230 |
| 7 | 17741762 |
| 8 | 23118462 |
| 9 | 19813118 |
| 10 | 75938021 |
+---------+-----------+
10 rows in set (0.00 sec)
| |
Lars L. Christensen (27-01-2006)
| Kommentar Fra : Lars L. Christensen |
Dato : 27-01-06 23:22 |
|
"Lars L. Christensen" <lars_christesen@ieee.org> wrote in
news:Xns9758EBEA9CC84larsperseusdkmaybefo@217.74.208.69:
> Michael Zedeler <michael@zedeler.dk> wrote in
> news:MrwCf.5607$Cl2.132451@news000.worldonline.dk:
>
>> Lars L. Christensen wrote:
>>> Michael Zedeler <michael@zedeler.dk> wrote in
>>> news:ye8Cf.5547$Cl2.132299@news000.worldonline.dk:
>>>
>>>
>>>>Lars L. Christensen wrote:
>>>>
>>>>>>>Desværre er det ikke altid 300, der er step-size på min dtime.
>>>>>>>Den kan variere fra 300 og op til 360. Der er derfor 3 entries =
>>>>>>>1 output, 3 entries = 1 output osv.
>>>>>>
>>>>>>Så har jeg ikke andre idéer, end at nummerere rækkerne fortløbende
>>>>>>(i feltet row_num)og bruge denne her:
>>>>>>
>>>>>>SELECT INT(row_num/3) AS row_group, AVG(counter)
>>>>>
>>>>>>FROM t1
>>>>>
>>>>>>GROUP BY row_group
>>>>>
>>>>>Jeg har gjort det nu, at jeg har "kopieret" de relevante data over
>>>>>i en temporær tabel og nummeret dem fortløbende. Dermed har jeg nu
>>>>>kun de data jeg skal bruge og de er nummeret fortløbende.
>>>>>
>>>>>Jeg synes ikke lige dine forslag lige vil.
>>>>
>>>>Hvad vil det sige at de ikke "lige vil"? Hvis du har puttet
>>>>fortløbende numre på dem, bør det virke. Hvad for fejl eller
>>>>resultater får du?
>>>
>>> mysql> select int(number/6) as row_grp, avg(counter) from temp group
>>> by row_grp;
>>> ERROR 1064 (42000): You have an error in your SQL syntax; check the
>>> manual that corresponds to your MySQL server version for the right
>>> syntax to use near 'int(number/6) as row_grp, avg(counter) from temp
>>> group by row_grp' at line 1
>>>
>>> Håber det giver en ide...
>>
>> Ja. Det gør det da. "number" er et reserveret ord. I mit eksempel
>> kalder jeg det også for noget andet.
>>
>> Mvh. Michael.
>
> Ok, det skal åbenbare bare ikke lige lykkes for mig i dag med den her
> query...
>
> Følgende output:
>
> mysql> create temporary table temp (row_num int not null
> auto_increment, counter bigint(20), primary key(row_num)) type = heap;
> Query OK, 0 rows affected, 1 warning (0.00 sec)
>
> mysql> insert into temp (counter) SELECT (i.counter/300)*8 FROM
> IntInOctets i where i.dtime < timestamp("2006-01-27 21:31:53") and
> i.dtime > timestamp("2006-01-20 21:31:53") and i.id = 20105 order by
> dtime;
> Query OK, 1452 rows affected (0.34 sec)
> Records: 1452 Duplicates: 0 Warnings: 0
>
> mysql> select int(row_num/6) as row_grp, avg(counter) from temp group
> by row_grp;
> ERROR 1064 (42000): You have an error in your SQL syntax; check the
> manual that corresponds to your MySQL server version for the right
> syntax to use near 'int(row_num/6) as row_grp, avg(counter) from temp
> group by row_grp' at line 1
> mysql> select * from temp limit 10;
> +---------+-----------+
>| row_num | counter |
> +---------+-----------+
>| 1 | 110319051 |
>| 2 | 22602889 |
>| 3 | 41405755 |
>| 4 | 21054075 |
>| 5 | 22419886 |
>| 6 | 21286230 |
>| 7 | 17741762 |
>| 8 | 23118462 |
>| 9 | 19813118 |
>| 10 | 75938021 |
> +---------+-----------+
> 10 rows in set (0.00 sec)
>
>
Aaaahhhh... tror jeg fandt løsningen...
select cast(row_num/6 as unsigned) as row_grp, avg(counter) from temp
group by row_grp;
Det ser ud til at virke, idet 1452 poster averaged over 6 giver 243
rækker som forventet...
lækkert :)
mvh
Lars
| |
Michael Zedeler (28-01-2006)
| Kommentar Fra : Michael Zedeler |
Dato : 28-01-06 15:31 |
|
Lars L. Christensen wrote:
> Aaaahhhh... tror jeg fandt løsningen...
>
> select cast(row_num/6 as unsigned) as row_grp, avg(counter) from temp
> group by row_grp;
Klart. beklager fejlen.
> Det ser ud til at virke, idet 1452 poster averaged over 6 giver 243
> rækker som forventet...
Ok. Det var da godt.
Mvh. Michael.
--
Which is more dangerous? TV guided missiles or TV guided families?
Visit my home page at http://michael.zedeler.dk/
Get my vcard at http://michael.zedeler.dk/vcard.vcf
| |
Nis Jorgensen (24-01-2006)
| Kommentar Fra : Nis Jorgensen |
Dato : 24-01-06 00:49 |
|
On 23 Jan 2006 23:33:06 +0100, "Lars L. Christensen"
<lars_christesen@ieee.org> wrote:
>
>Hejsa
>
>Jeg har en udfordring, som jeg ikke helt lige ved hvordan jeg skal klare.
>
>Jeg har en tabel t1, som indeholder dtime og counter. dtime er en
>timestamp i 5 minutters intervaller og counter er en counter.
>
>I tabellen har jeg en pæn mængde data (1 mio records). Jeg ønsker at
>trække data ud, således at jeg f.eks. kun har 300 records, men af disse
>300 records skal de være averages af f.eks. 900 records, således at for
>hver 3 records skal der tages en average og denne average skal så bruges.
>
>Jeg håber det giver lidt mening...
>
>Eksempel
>
>t1.dtime t1.counter
>2000300 1
>2000600 2
>2000900 3
>2001200 500
>2001500 1000
>2001800 1250
>
>Disse infos skal give et output i stil med:
>
>t1.dtime t1.counter
>2000900 2
>1001800 916,67
>
>
>Håber der er nogen der har en god ide...
Noget i retning af
SELECT max(dtime), AVG(counter)
FROM t1
GROUP BY int(dtime/300)
--
Nis Jørgensen
Udlandsbornholmer
| |
|
|