Nie jesteś zalogowany.
Jeśli nie posiadasz konta, zarejestruj je już teraz! Pozwoli Ci ono w pełni korzystać z naszego serwisu. Spamerom dziękujemy!
Prosimy o pomoc dla małej Julki — przekaż 1% podatku na Fundacji Dzieciom zdazyć z Pomocą.
Więcej informacji na dug.net.pl/pomagamy/.
Witam,
Zbieram dane z termometrów do pliku, a temperatura jest zapisywana jest z czasem Unix.
W jaki sposób wyczyścić dane z pliku starsze niż 30 dni?
Format danych:
[1406225590000,18.00],[1406225705000,18.00],[1406226005000,18.00],[1406226304000,18.00],[1406226605000,18.00], (...)
Z góry dziękuję za pomoc.
Offline
Nikt nie ma pomysłu jak to zrobić?
Czy po prostu nie da się zrobić takich rzeczy?
Offline
Przy każdym dodaniu [...] na końcu pliku usuń [...] z początku pliku? (tylko warunek startowy - musi być ileśtam [...] w pliku; możesz go zainicjować pustymi "sekcjami" na przykład...
Basha nie znam więc nie napiszę jak to w skrypcie ma wyglądać, ale idea chyba zadziała.
Offline
A ja mam propozycje innego algorytmu:
- sprawdz czas teraz
- sprawdz czas temperatury
- jesli czas teraz jest wiekszy od czasu temperatury o 30 dni, to usun a jesli nie to zostaw
Czyli bash, narzedzie do przetwarzania tekstu i przykladowo odejmowanie zmiennych.
Nie wiem tylko jak to komputerowi przekazac.
Ostatnio edytowany przez Pavlo950 (2014-09-21 08:39:55)
Offline
Algorytm widzę następująco:
1. Zamień aktualny czas na unixowy.
2. Jeżeli AKTUALNY_CZAS - CZAS_Z_POMIARU > 2592000 Usuń
Czyli wydobywasz komplety [czas,pomiar] i sprawdzasz czy różnica jest większa niż 2592000. Jeżeli jest większa oznacza to, że pomiar jest starszy niż 30 dni :)
Ostatnio edytowany przez Piotr3ks (2014-09-21 14:33:05)
Offline
Kolega z elektroda.pl mi pomógł i wyszedł skrypt Bash, który czyści dane starsze niż 3 miesiące:
#!/bin/bash timeNow=`date +%s` echo "Czas teraz: ""$timeNow" timeNow=$[timeNow-7889232] timeNow=$[timeNow*1000] echo "Czas teraz - miesiac: ""$timeNow" plik=/var/www/0.txt plikNowy=/var/www/0.nowy.txt daneNowe=`awk -v x="$timeNow" ' \ BEGIN { RS="["; FS=","; CONVFMT = "%.16g"; ORS=""; OFS="" } \ { \ if (($1 > x) && ($1>0)) print "["$1","$2"," ; \ } \ ' "$plik" ` echo "$daneNowe" > "$plikNowy" echo "$daneNowe"
Offline
Sporo zbednych operacji
date --date="30 days ago" +%s
I mamy czas 30 dni od aktualnego bez zbędnej matematyki, a w razie potrzeby mozna bardzo latwo zmienic ilosc dni.
A żeby pozbyć się mnożenia
zmienna="`date --date="30 days ago" +%s`000"
Offline
Czy tak to ma wyglądać?
#!/bin/bash timeNow="`date --date="90 days ago" +%s`000" plik=/var/www/0.txt plikNowy=/var/www/0.nowy.txt daneNowe=`awk -v x="$timeNow" ' \ BEGIN { RS="["; FS=","; CONVFMT = "%.16g"; ORS=""; OFS="" } \ { \ if (($1 > x) && ($1>0)) print "["$1","$2"," ; \ } \ ' "$plik" ` echo "$daneNowe" > "$plikNowy"
Offline
Tak, choć drugą cześć też da się łatwiej zrobić, pomyśle o czymś w weekend. :)
Offline
[quote=qluk]Tak, choć drugą cześć też da się łatwiej zrobić, pomyśle o czymś w weekend. :)[/quote]
Z góry dziękuje ;)
Offline
[quote=pimowo]Witam,
Zbieram dane z termometrów do pliku, a temperatura jest zapisywana jest z czasem Unix.
W jaki sposób wyczyścić dane z pliku starsze niż 30 dni?
Format danych:
[1406225590000,18.00],[1406225705000,18.00],[1406226005000,18.00],[1406226304000,18.00],[1406226605000,18.00], (...)
Z góry dziękuję za pomoc.[/quote]
Pytania:
1) skad są te dodatkowe zera na końcu sygnatury czasu?
2) rozumie że plik to jeden ciąg znaków bez znaków nowej linii?
3) czy temperatury poniżej 10 są zapisywane z zerem wiodącym?
4) ujemne posiadają znak?
Offline
Może będzie lepiej jak [s]pokarze[/s] pokażę kod, który zbiera dane termometrów
<?php $path = "/var/www/"; // Sciezka gdzie bedzie zapisywalo dane, domyslnie /www/meteo/ system("digitemp_DS9097 -a > /var/www/meteo2.txt && mv /var/www/meteo2.txt /var/www/meteo.txt"); ini_set( 'date.timezone', 'Europe/Berlin' ); $a = array(); $e = explode("Sensor ",file_get_contents("/var/www/meteo.txt")); unset($e[0]); foreach($e as $v) { $e1 = explode(" ",$v); $id = $e1[0]; // Id Termometra $temp = $e1[2]; // Temperatura na termometrze if(file_exists($path.$id.".txt")) file_put_contents($path.$id.".txt",",[".time(NULL)."000,".$temp."]",FILE_APPEND); else file_put_contents($path.$id.".txt","[".time(NULL)."000,".$temp."]",FILE_APPEND); $a[($id)] = $temp; } file_put_contents($path."last.txt",serialize($a)); // ostatnie dane system('digitemp_DS9097 -t 0 -q -o "%.2C" > /home/serwer/temperatura/ulica.txt'); system('digitemp_DS9097 -t 5 -q -o "%.2C" > /home/serwer/temperatura/salon.txt'); ?>
Ostatnio edytowany przez azhag (2014-09-26 22:17:24)
Offline
Jak masz kod php, który zbiera z termometrów, to niech lepiej ten kod zacznie pakować wyniki do bazy SQL, każdy tydzień lub miesiąc w osobnej tabeli, i wtedy wybieranie czy kasowanie poszczególnych rezultatów będzie równie trudne, co zjedzenie bułki z masłem.
Do wyboru masz Mysql, Postgresql, Sqlite albo Firebirda, PHP obrabia te wszystkie bazy, da się też zapiąć PHP do Oracla albo MSSQL.
Ostatnio edytowany przez Jacekalex (2014-09-27 00:43:08)
Offline
Gdybym ja potrafił napisać sobie takie skomplikowane programy/kody/skrypty to bym na pewno zrobił bazę np. Mysql i tam wrzucał wszystkie wyniki i nic nie kasował. Nie pogardziłbym danymi z 3, 6 czy tam 12 miesięcy :) Ale cóż wiedzy brak :(
Przy tym co mam pojawił się problem "zamulania" skryptu gdy danych jest więcej niż 3-4 miesiące i stad pomysł kasowania danych.
Termometrów w sumie mam 8-docelowo będzie 12szt.
Offline
To jeszcze jedno pytanie.... Jaki jest powód że to jest w PHP?
Jacekalex: Do tak małych danych mySQL? Już prędzej record file.
Offline
Nie wiem. Skrypty znalazłem w Internecie, a dokładnie na forum eko.one.pl
Są w sumie dwa skrypty:
-ten który dałem wcześniej,
-skrypt który "rysuje" wykresy (również PHP)
<?php $id = $_GET['id']; $temp = array(); $all = false; $temp[0] = array("name" => "Ulica", "all" => true); $temp[1] = array("name" => "Podwórko", "all" => true); $temp[2] = array("name" => "Łazienka", "all" => true); $temp[3] = array("name" => "Sypialnia", "all" => true); $temp[4] = array("name" => "Boys", "all" => true); $temp[5] = array("name" => "Salon", "all" => true); $temp[6] = array("name" => "Kuchnia", "all" => true); $temp[7] = array("name" => "Korytarz", "all" => true); foreach(unserialize(file_get_contents("last.txt")) as $i => $t) { if(isset($temp[($i)])) $temp[($i)]["temp"] = $t; // Obecna Temp } if(!isset($temp[($id)])) // Gdy brak id to pokazuj wszystkie czujniki z parametrem all = true $all = true; ?> <!DOCTYPE HTML> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"> <title>temperatura</title> <link rel="shortcut icon" href="pimowo.ico" /> <script type="text/javascript" src="js/jquery-1.8.3.min.js"></script> <script type="text/javascript"> $(function() { Highcharts.setOptions({ lang: { months: ['Styczeń', 'Luty', 'Marzec', 'Kwiecień', 'Maj', 'Czerwiec', 'Lipiec', 'Śierpień', 'Wrzesień', 'Październik', 'Listopad', 'Grudzień'], weekdays: ['Nie', 'Pon', 'Wt', 'Śr', 'Czw', 'Pt', 'Sob'] }, global: { useUTC: false } }), window.chart = new Highcharts.StockChart({ chart: { renderTo: 'container' }, xAxis: { type: 'datetime', dateTimeLabelFormats: { second: '%d-%m-%y<br/>%H:%M:%S', minute: '%d-%m<br/>%H:%M', hour: '%d-%m<br/>%H:%M', day: '%Y<br/>%d-%m', week: '%Y<br/>%d-%m', month: '%m-%Y', year: '%Y' } }, rangeSelector: { buttons: [{ type: 'day', count: 1, text: '1d' }, { type: 'day', count: 7, text: '7d' }, { type: 'month', count: 1, text: '1m' }, { type: 'month', count: 3, text: '3m' }], selected: 0 }, title: { text: '<?php echo ($all ? "Temperatura" : "Temperatura - ".$temp[($id)]['name']); ?>' }, yAxis: { title: { text: 'Temperatura ( °C )' }, }, <?php if(!$all) { echo "series: [{ name: 'Temperatura', data: [".file_get_contents($id.'.txt')."], type: 'spline', shadow: true, tooltip: { valueDecimals: 2, valueSuffix: '°C' } }] "; } else { echo "series: ["; $f = false; foreach($temp as $k => $v) { if(!$v['all']) continue; if($f) echo ","; echo "{ name: '".$v['name']."', data: [".file_get_contents($k.'.txt')."], type: 'spline', shadow: true, tooltip: { valueDecimals: '2', valueSuffix: ' °C' } }"; $f = true; } echo "] "; } ?> }); }); </script> </head> <body> <script src="js/highstock.js"></script> <script src="js/modules/exporting.js"></script> <script type="text/javascript" src="js/themes/gray.js"></script> <b> <a href="?"> Wykres wszystkich termometrów </a></b> <table rules="all" border=1 width="100%"><tr width="100%"> <br /> <br /> <?php $cd = ""; foreach($temp as $k => $v) { echo '<td align="center"><a href="?id='.$k.'">'.$v["name"].'</a></td>'; $cd .= '<td align="center">'.$v["temp"].'</td>'; } echo "</tr><tr>".$cd."</tr>" ?> </table><br> <div id="container" style="height: 370px"></div><br> </div> </center> </body> </html>
A może zamiast kombinować i kasować dane to da się jakoś zrobić "normalną" bazę danych?
Ostatnio edytowany przez pimowo (2014-09-26 23:09:32)
Offline
[quote=qluk]To jeszcze jedno pytanie.... Jaki jest powód że to jest w PHP?
Jacekalex: Do tak małych danych mySQL? Już prędzej record file.[/quote]
SQlite nie jest ani wielki, ani ciężki, też da radę.
Poza tym co ile sekund taki pomiar jest zapisywany?
Bo jak np 10 razy na sekundę, to i Mysql może być za słaby. :D
Offline
[quote=Jacekalex]Poza tym co ile sekund taki pomiar jest zapisywany?
Bo jak np 10 razy na sekundę, to i Mysql może być za słaby. :D[/quote]
Masz przykładowe dane z timestampami to sobie policz co ile jest zapisywany ;p
Offline
Pomiar jest co 5 minut.
Offline
[quote=winnetou][quote=Jacekalex]Poza tym co ile sekund taki pomiar jest zapisywany?
Bo jak np 10 razy na sekundę, to i Mysql może być za słaby. :D[/quote]
Masz przykładowe dane z timestampami to sobie policz co ile jest zapisywany ;p[/quote]
Nawet jakbym miał przykładowe, to na razie jest 8 termometrów,
a to nie oznacza, że z alledrogo nie idzie następne 200 termometrów.
Poza tym ja tam nie mam parcia na rejestrowanie temperatur w okolicy. :D
Offline
[quote=Jacekalex][quote=winnetou][quote=Jacekalex]Poza tym co ile sekund taki pomiar jest zapisywany?
Bo jak np 10 razy na sekundę, to i Mysql może być za słaby. :D[/quote]
Masz przykładowe dane z timestampami to sobie policz co ile jest zapisywany ;p[/quote]
Nawet jakbym miał przykładowe, to na razie jest 8 termometrów,
a to nie oznacza, że z alledrogo nie idzie następne 200 termometrów.
Poza tym ja tam nie mam parcia na rejestrowanie temperatur w okolicy. :D[/quote]
[quote=pimowo]Termometrów w sumie mam 8-docelowo będzie 12szt.[/quote]
Offline
To chyba najlepszy byłby SQlite, chociaż ja bym zatrudnił Mysqla.
Poradników w typie Php i Sql masz kilka tysi na necie, jakbyś te skrypty chciał przeżeźbić na SQL, to jest bardziej niż wykonalne.
Ten jest chyba najlepszy angielski:
http://www.w3schools.com/php/php_mysql_intro.asp
Po polsku też jest tego trochę.
Ostatnio edytowany przez Jacekalex (2014-09-27 02:35:20)
Offline
Czyli z tego co mówisz to najlepiej by było zrobić bazę danych z prawdziwego zdarzenia, a nie zapisywać danych w formie txt.
W sumie to nie musiałbym kasować żadnych danych. Czyli jak dla mnie jeszcze większa funkcjonalność :)
Offline
Też musiałbyś kasować, bo dyzie to nie gumki od majtek, tylko w SQL to banalnie proste, np
DELETE FROM wyniki WHERE timestamp < UNIX_TIMESTAMP('wartość');
Strasznie trudne, prawda?
Offline
Time (s) | Query |
---|---|
0.00010 | SET CHARSET latin2 |
0.00004 | SET NAMES latin2 |
0.00093 | SELECT u.*, g.*, o.logged FROM punbb_users AS u INNER JOIN punbb_groups AS g ON u.group_id=g.g_id LEFT JOIN punbb_online AS o ON o.ident='3.135.202.38' WHERE u.id=1 |
0.00097 | REPLACE INTO punbb_online (user_id, ident, logged) VALUES(1, '3.135.202.38', 1732553342) |
0.00056 | SELECT * FROM punbb_online WHERE logged<1732553042 |
0.00048 | SELECT topic_id FROM punbb_posts WHERE id=276561 |
0.00014 | SELECT id FROM punbb_posts WHERE topic_id=26360 ORDER BY posted |
0.00054 | SELECT t.subject, t.closed, t.num_replies, t.sticky, f.id AS forum_id, f.forum_name, f.moderators, fp.post_replies, 0 FROM punbb_topics AS t INNER JOIN punbb_forums AS f ON f.id=t.forum_id LEFT JOIN punbb_forum_perms AS fp ON (fp.forum_id=f.id AND fp.group_id=3) WHERE (fp.read_forum IS NULL OR fp.read_forum=1) AND t.id=26360 AND t.moved_to IS NULL |
0.00005 | SELECT search_for, replace_with FROM punbb_censoring |
0.00107 | SELECT u.email, u.title, u.url, u.location, u.use_avatar, u.signature, u.email_setting, u.num_posts, u.registered, u.admin_note, p.id, p.poster AS username, p.poster_id, p.poster_ip, p.poster_email, p.message, p.hide_smilies, p.posted, p.edited, p.edited_by, g.g_id, g.g_user_title, o.user_id AS is_online FROM punbb_posts AS p INNER JOIN punbb_users AS u ON u.id=p.poster_id INNER JOIN punbb_groups AS g ON g.g_id=u.group_id LEFT JOIN punbb_online AS o ON (o.user_id=u.id AND o.user_id!=1 AND o.idle=0) WHERE p.topic_id=26360 ORDER BY p.id LIMIT 0,25 |
0.00093 | UPDATE punbb_topics SET num_views=num_views+1 WHERE id=26360 |
Total query time: 0.00581 s |