Text processing/1: Difference between revisions

m
m (→‎{{header|Wren}}: Minor tidy)
 
(26 intermediate revisions by 13 users not shown)
Line 20:
 
The data is [http://www.eea.europa.eu/help/eea-help-centre/faqs/how-do-i-obtain-eea-reports free to download and use] and is of this format:
 
Data is no longer available at that link. Zipped mirror available [https://github.com/thundergnat/rc/blob/master/resouces/readings.zip here] (offsite mirror).
<pre style="overflow:scroll">
1991-03-30 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1
Line 32 ⟶ 34:
 
Structure your program to show statistics for each line of the file, (similar to the original Python, Perl, and AWK examples below), followed by summary statistics for the file. When showing example output just show a few line statistics and the full end summary.
 
=={{header|11l}}==
{{trans|Python}}
 
<syntaxhighlight lang="11l">V nodata = 0
V nodata_max = -1
[String] nodata_maxline
V tot_file = 0.0
V num_file = 0
 
:start:
L(line) File(:argv[1]).read().rtrim("\n").split("\n")
V tot_line = 0.0
V num_line = 0
 
V field = line.split("\t")
V date = field[0]
V data = field[(1..).step(2)].map(f -> Float(f))
V flags = field[(2..).step(2)].map(f -> Int(f))
 
L(datum, flag) zip(data, flags)
I flag < 1
nodata++
E
I nodata_max == nodata & nodata > 0
nodata_maxline.append(date)
I nodata_max < nodata & nodata > 0
nodata_max = nodata
nodata_maxline = [date]
nodata = 0
tot_line += datum
num_line++
 
tot_file += tot_line
num_file += num_line
 
print(‘Line: #11 Reject: #2 Accept: #2 Line_tot: #6.3 Line_avg: #6.3’.format(
date, data.len - num_line, num_line, tot_line, I (num_line > 0) {tot_line / num_line} E 0))
 
print()
print(‘File(s) = #.’.format(:argv[1]))
print(‘Total = #6.3’.format(tot_file))
print(‘Readings = #6’.format(num_file))
print(‘Average = #6.3’.format(tot_file / num_file))
print("\nMaximum run(s) of #. consecutive false readings ends at line starting with date(s): #.".format(nodata_max, nodata_maxline.join(‘, ’)))</syntaxhighlight>
 
{{out}}
<pre>
...
Line: 2004-12-29 Reject: 1 Accept: 23 Line_tot: 56.300 Line_avg: 2.448
Line: 2004-12-30 Reject: 1 Accept: 23 Line_tot: 65.300 Line_avg: 2.839
Line: 2004-12-31 Reject: 1 Accept: 23 Line_tot: 47.300 Line_avg: 2.057
 
File(s) = readings.txt
Total = 1358393.400
Readings = 129403
Average = 10.497
 
Maximum run(s) of 589 consecutive false readings ends at line starting with date(s): 1993-03-05
</pre>
 
=={{header|Ada}}==
{{libheader|Simple components for Ada}}
<langsyntaxhighlight lang="ada">with Ada.Text_IO; use Ada.Text_IO;
with Strings_Edit; use Strings_Edit;
with Strings_Edit.Floats; use Strings_Edit.Floats;
Line 110 ⟶ 172:
Close (File);
Put_Line ("Syntax error at " & Image (Current.Line) & ':' & Image (Max.Pointer));
end Data_Munging;</langsyntaxhighlight>
The implementation performs minimal checks. The average is calculated over all valid data. For the maximal chain of consequent invalid data, the source line number, the column number, and the time stamp of the first invalid data is printed.
{{out|Sample output}}
Line 117 ⟶ 179:
Max. 589 false readings start at 1136:20 stamped 1993-2-9
</pre>
 
=={{header|Aime}}==
<syntaxhighlight lang="aime">integer bads, count, max_bads;
file f;
list l;
real s;
text bad_day, worst_day;
 
f.stdin;
 
max_bads = count = bads = s = 0;
 
while (f.list(l, 0) ^ -1) {
integer i;
 
i = 2;
while (i < 49) {
if (0 < atoi(l[i])) {
count += 1;
s += atof(l[i - 1]);
if (max_bads < bads) {
max_bads = bads;
worst_day = bad_day;
}
bads = 0;
} else {
if (!bads) {
bad_day = l[0];
}
bads += 1;
}
i += 2;
}
}
 
o_form("Averaged /d3/ over ~ readings.\n", s / count, count);
o_("Longest bad run ", max_bads, ", started ", worst_day, ".\n");</syntaxhighlight>
Run as:
<pre>cat readings.txt | tr -d \\r | aime SOURCE_FILE</pre>
{{out}}
<pre>Averaged 10.497 over 129403 readings.
Longest bad run 589, started 1993-02-09.</pre>
 
=={{header|ALGOL 68}}==
Line 123 ⟶ 227:
{{works with|ALGOL 68G|Any - tested with release mk15-0.8b.fc9.i386}}
<!--{{does not work with|ELLA ALGOL 68|Any (with appropriate job cards) - argc and argv are extensions}} -->
<langsyntaxhighlight lang="algol68">INT no data := 0; # Current run of consecutive flags<0 in lines of file #
INT no data max := -1; # Max consecutive flags<0 in lines of file #
FLEX[0]STRING no data max line; # ... and line number(s) where it occurs #
Line 217 ⟶ 321:
upb list := UPB no data max line;
printf(($l"Maximum run"f(p)" of "g(-0)" consecutive false reading"f(p)" ends at line starting with date"f(p)": "$,
upb list = 1, no data max, no data max = 0, upb list = 1, list repr, no data max line, $l$))</langsyntaxhighlight>
Command:
$ a68g ./Data_Munging.a68 - data
Line 236 ⟶ 340:
Maximum run of 24 consecutive false readings ends at line starting with date: 1991-04-01
</pre>
 
=={{header|Aime}}==
<lang aime>integer bads, count, max_bads;
file f;
list l;
real s;
text bad_day, worst_day;
 
f_affix(f, "/dev/stdin");
 
max_bads = 0;
count = 0;
bads = 0;
s = 0;
 
while (f_list(f, l, 0) ^ -1) {
integer e, i;
 
i = 2;
while (i < 49) {
e = atoi(l_q_text(l, i));
if (0 < e) {
count += 1;
s += atof(l_q_text(l, i - 1));
if (max_bads < bads) {
max_bads = bads;
worst_day = bad_day;
}
bads = 0;
} else {
if (!bads) {
bad_day = l_q_text(l, 0);
}
bads += 1;
}
i += 2;
}
}
 
o_text("Averaged ");
o_real(3, s / count);
o_text(" over ");
o_integer(count);
o_text(" readings.\n");
 
o_text("Longest bad run ");
o_integer(max_bads);
o_text(", started ");
o_text(worst_day);
o_text(".\n");</lang>
Run as:
<pre>cat readings.txt | tr -d \\r | aime SOURCE_FILE</pre>
{{out}}
<pre>Averaged 10.497 over 129403 readings.
Longest bad run 589, started 1993-02-09.</pre>
 
=={{header|AutoHotkey}}==
<langsyntaxhighlight AutoHotkeylang="autohotkey"># Author AlephX Aug 17 2011
 
SetFormat, float, 4.2
Line 366 ⟶ 415:
Totavg := TotSum / TotValid
FileAppend, `n`nDays %Lines%`nMaximal wrong readings: %maxwrong% from %startwrongdate% at %startoccurrence% to %lastwrongdate% at %lastoccurrence%`n`n, %result%
FileAppend, Valid readings: %TotValid%`nTotal Value: %TotSUm%`nAverage: %TotAvg%, %result%</langsyntaxhighlight>
{{out|Sample output}}
<pre>Day: 1990-01-01 sum: 590.00 avg: 26.82 Readings: 22/24.00
Line 385 ⟶ 434:
 
=={{header|AWK}}==
<langsyntaxhighlight lang="awk">BEGIN{
nodata = 0; # Current run of consecutive flags<0 in lines of file
nodata_max=-1; # Max consecutive flags<0 in lines of file
Line 447 ⟶ 496:
 
printf "\nMaximum run(s) of %i consecutive false readings ends at line starting with date(s): %s\n", nodata_max, nodata_maxline
}</langsyntaxhighlight>
{{out|Sample output}}
<pre>bash$ awk -f readings.awk readings.txt | tail
Line 463 ⟶ 512:
 
=={{header|Batch File}}==
<langsyntaxhighlight lang="dos">@echo off
setlocal ENABLEDELAYEDEXPANSION
set maxrun= 0
Line 529 ⟶ 578:
echo Line: %date% Accept: %count:~-3% tot: %sum:~-8% avg: %mean:~-8%
 
goto :EOF</langsyntaxhighlight>
{{out}}
<pre>
Line 551 ⟶ 600:
 
=={{header|BBC BASIC}}==
<langsyntaxhighlight lang="bbcbasic"> file% = OPENIN("readings.txt")
IF file% = 0 THEN PRINT "Could not open test data file" : END
Line 593 ⟶ 642:
PRINT "Overall mean = " ; Total / Count%
@% = &90A
PRINT '"Longest run of bad readings = " ; BadMax% " ending " BadDate$</langsyntaxhighlight>
{{out}}
<pre>
Line 616 ⟶ 665:
 
=={{header|C}}==
<langsyntaxhighlight lang="c">#include <stdio.h>
#include <stdlib.h>
#include <string.h>
Line 700 ⟶ 749:
fclose(outfile);
return 0;
}</langsyntaxhighlight>
{{out|Sample output}}
<pre>1990-01-01 Reject: 2 Accept: 22 Average: 26.818
Line 717 ⟶ 766:
 
=={{header|C++}}==
<langsyntaxhighlight Cpplang="cpp">#include <iostream>
#include <fstream>
#include <string>
Line 783 ⟶ 832:
cout << "Maximum number of consecutive bad readings is " << badCountMax << endl;
cout << "Ends on date " << badDate << endl;
}</langsyntaxhighlight>
{{out}}
<pre>1990-01-01 Reject: 2 Accept: 22 Average: 26.818
Line 793 ⟶ 842:
Maximum number of consecutive bad readings is 589
Ends on date 1993-03-05</pre>
 
 
=={{header|Clojure}}==
<syntaxhighlight lang="clojure">
(ns rosettacode.textprocessing1
(:require [clojure.string :as str]))
 
(defn parse-line [s]
(let [[date & data-toks] (str/split s #"\s+")]
{:date date
:hour-vals (for [[v flag] (partition 2 data-toks)]
{:val (Double. v)
:flag (Long. flag)})}))
 
(defn analyze-line [m]
(let [valid? (fn [rec] (pos? (:flag rec)))
data (->> (filter valid? (:hour-vals m))
(map :val))
n-vals (count data)
sum (reduce + data)]
{:date (:date m)
:n-vals n-vals
:sum (double sum)
:avg (if (zero? n-vals) 0.0 (/ sum n-vals))
:gaps (for [hr (:hour-vals m)]
{:gap? (not (valid? hr)) :date (:date m)})}))
 
(defn print-line [m]
(println (format "%s: %d valid, sum: %7.3f, mean: %6.3f"
(:date m)
(:n-vals m)
(:sum m)
(:avg m))))
 
(defn process-line [s]
(let [m (parse-line s)
line-info (analyze-line m)]
(print-line line-info)
line-info))
 
(defn update-file-stats [file-m line-m]
(let [append (fn [a b] (reduce conj a b))]
(-> file-m
(update-in [:sum] + (:sum line-m))
(update-in [:n-vals] + (:n-vals line-m))
(update-in [:gap-recs] append (:gaps line-m)))))
 
(defn process-file [path]
(let [file-lines (->> (slurp path)
str/split-lines)
summary (reduce (fn [res line]
(update-file-stats res (process-line line)))
{:sum 0
:n-vals 0
:gap-recs []}
file-lines)
max-gap (->> (partition-by :gap? (:gap-recs summary))
(filter #(:gap? (first %)))
(sort-by count >)
first)]
(println (format "Sum: %f\n# Values: %d\nAvg: %f"
(:sum summary)
(:n-vals summary)
(/ (:sum summary) (:n-vals summary))))
(println (format "Max gap of %d recs started on %s"
(count max-gap)
(:date (first max-gap))))))
</syntaxhighlight>
 
{{out}}
<pre>
... Many lines elided ...
2004-12-24: 23 valid, sum: 67.500, mean: 2.935
2004-12-25: 23 valid, sum: 137.500, mean: 5.978
2004-12-26: 23 valid, sum: 154.600, mean: 6.722
2004-12-27: 23 valid, sum: 57.100, mean: 2.483
2004-12-28: 23 valid, sum: 77.800, mean: 3.383
2004-12-29: 23 valid, sum: 56.300, mean: 2.448
2004-12-30: 23 valid, sum: 65.300, mean: 2.839
2004-12-31: 23 valid, sum: 47.300, mean: 2.057
 
Sum: 1358393.400000
# Values: 129403
Avg: 10.497387
 
Max gap of 589 recs started on 1993-02-09
</pre>
 
=={{header|COBOL}}==
<langsyntaxhighlight lang="cobol"> IDENTIFICATION DIVISION.
PROGRAM-ID. data-munging.
 
Line 938 ⟶ 1,074:
 
GOBACK
.</langsyntaxhighlight>
 
{{Out|Example output}}
Line 961 ⟶ 1,097:
 
=={{header|Common Lisp}}==
<langsyntaxhighlight lang="lisp">(defvar *invalid-count*)
(defvar *max-invalid*)
(defvar *max-invalid-date*)
Line 1,008 ⟶ 1,144:
(format t "~%Maximum run(s) of ~a consecutive false readings ends at ~
line starting with date(s): ~a~%"
*max-invalid* *max-invalid-date*)))</langsyntaxhighlight>
{{out|Example output}}
<pre>...
Line 1,024 ⟶ 1,160:
=={{header|D}}==
{{trans|Python}}
<langsyntaxhighlight lang="d">void main(in string[] args) {
import std.stdio, std.conv, std.string;
 
Line 1,098 ⟶ 1,234:
"readings ends at line starting with date(s): %-(%s, %)",
noDataMax, noDataMaxLine);
}</langsyntaxhighlight>
The output matches that of the [[#Python|Python]] version.
 
=={{header|Eiffel}}==
<syntaxhighlight lang="eiffel">
<lang Eiffel>
class
APPLICATION
Line 1,222 ⟶ 1,358:
 
end
</syntaxhighlight>
</lang>
{{out}}
Only the last three lines of the per line summary statistics are shown.
Line 1,243 ⟶ 1,379:
The function file_contents/1 is used by [[Text_processing/2]]. Please update the user if you make any interface changes.
 
<syntaxhighlight lang="erlang">
<lang Erlang>
-module( text_processing ).
 
Line 1,310 ⟶ 1,446:
{_Previous, Value_flags} = lists:foldr( fun file_content_line_value_flag/2, {[], []}, Rest ), % Preserve order
{binary:bin_to_list( Date_binary ), Value_flags}.
</syntaxhighlight>
</lang>
{{out}}
<pre>
Line 1,330 ⟶ 1,466:
=={{header|Forth}}==
{{works with|GNU Forth}}
<langsyntaxhighlight lang="forth">\ data munging
 
\ 1991-03-30[\t10.000\t[-]1]*24
Line 1,422 ⟶ 1,558:
total-sum f@ total-n @ .mean cr ;
 
main bye</langsyntaxhighlight>
 
=={{header|Fortran}}==
Line 1,433 ⟶ 1,569:
Incidentally, a daily average of a set of measurements may be unsuitable when data are missing, as when there is a regular pattern over a day. The N.Z. electricity supply association ruled that in calculating the ratio of daytime to nighttime usage, should there be four or more missing data in a day, then the entire day's data were to be rejected when computing the monthly or quarterly ratio.
 
<syntaxhighlight lang="fortran">
<lang Fortran>
Crunches a set of hourly data. Starts with a date, then 24 pairs of value,indicator for that day, on one line.
INTEGER Y,M,D !Year, month, and day.
Line 1,526 ⟶ 1,662:
900 CLOSE(IN) !Done.
END !Spaghetti rules.
</syntaxhighlight>
</lang>
 
Output:
Line 1,541 ⟶ 1,677:
 
=={{header|Go}}==
<langsyntaxhighlight lang="go">package main
 
import (
Line 1,631 ⟶ 1,767:
maxRun, maxDate)
}
}</langsyntaxhighlight>
{{out}}
<pre>
Line 1,649 ⟶ 1,785:
 
=={{header|Haskell}}==
<langsyntaxhighlight Haskelllang="haskell">import Data.List
import Numeric
import Control.Arrow
Line 1,695 ⟶ 1,831:
(\(t,n) -> printf totalFmt n t (t/fromIntegral n)) $ fst summ
mapM_ ((\(l, d1,d2) -> printf maxFmt l d1 d2)
. (\(a,b)-> (a,(fst.(dat!!).(`div`24))b,(fst.(dat!!).(`div`24))(a+b)))) $ snd summ</langsyntaxhighlight>
{{out}}
<langsyntaxhighlight Haskelllang="haskell">*Main> :main ["./RC/readings.txt"]</langsyntaxhighlight>
<pre>Some lines:
 
Line 1,710 ⟶ 1,846:
 
=={{header|Icon}} and {{header|Unicon}}==
<langsyntaxhighlight Iconlang="icon">record badrun(count,fromdate,todate) # record to track bad runs
 
procedure main()
Line 1,760 ⟶ 1,896:
else
write(fout,"No bad runs of data")
end</langsyntaxhighlight>
{{out|Sample output}}
<pre>...
Line 1,776 ⟶ 1,912:
=={{header|J}}==
'''Solution:'''
<langsyntaxhighlight lang="j"> load 'files'
parseLine=: 10&({. ,&< (_99&".;._1)@:}.) NB. custom parser
summarize=: # , +/ , +/ % # NB. count,sum,mean
Line 1,789 ⟶ 1,925:
589
]StartDates=: Dates {~ (>:@I.@e.&MaxRun (24 <.@%~ +/)@{. ]) RunLengths
1993-03-05</langsyntaxhighlight>
'''Formatting Output'''<br>
Define report formatting verbs:
<langsyntaxhighlight lang="j">formatDailySumry=: dyad define
labels=. , ];.2 'Line: Accept: Line_tot: Line_avg: '
labels , x ,. 7j0 10j3 10j3 ": y
Line 1,802 ⟶ 1,938:
'maxrun dates'=. x
out=. out,LF,'Maximum run(s) of ',(": maxrun),' consecutive false readings ends at line(s) starting with date(s): ',dates
)</langsyntaxhighlight>
{{out|Show output}}
<langsyntaxhighlight lang="j"> (_4{.Dates) formatDailySumry _4{. DailySummary
Line: Accept: Line_tot: Line_avg:
2004-12-28 23 77.800 3.383
Line 1,816 ⟶ 1,952:
Average: 10.497
 
Maximum run(s) of 589 consecutive false readings ends at line(s) starting with date(s): 1993-03-05</langsyntaxhighlight>
 
=={{header|Java}}==
{{works with|Java|7}}
<langsyntaxhighlight lang="java">import java.io.File;
import java.util.*;
import static java.lang.System.out;
Line 1,908 ⟶ 2,044:
}
}
}</langsyntaxhighlight>
 
<pre>1990-01-01 out: 2 in: 22 tot: 590.000 avg: 26.818
Line 1,923 ⟶ 2,059:
=={{header|JavaScript}}==
{{works with|JScript}}
<langsyntaxhighlight lang="javascript">var filename = 'readings.txt';
var show_lines = 5;
var file_stats = {
Line 1,991 ⟶ 2,127:
function dec3(value) {
return Math.round(value * 1e3) / 1e3;
}</langsyntaxhighlight>
{{out}}
<pre>Line: 1990-01-01 Reject: 2 Accept: 22 Line_tot: 590 Line_avg: 26.818
Line 2,014 ⟶ 2,150:
 
The "foreach" syntax is:
<langsyntaxhighlight lang="jq">foreach STREAM as $row ( INITIAL; EXPRESSION; VALUE ).</langsyntaxhighlight>
The basic idea is that for each $row in STREAM, the value specified by VALUE is emitted.
 
If we wished only to produce per-line synopses of the "readings.txt"
file, the following pattern could be used:
<langsyntaxhighlight lang="jq">foreach (inputs | split("\t")) as $line (INITIAL; EXPRESSION; VALUE)</langsyntaxhighlight>
In order to distinguish the single-line synopsis from the whole-file synopsis, we will use the following pattern instead:
<langsyntaxhighlight lang="jq">foreach ((inputs | split("\t")), null) as $line (INITIAL; EXPRESSION; VALUE)</langsyntaxhighlight>
The "null" is added so that the stream of per-line values can be distinguished from the last value in the stream.
 
Line 2,027 ⟶ 2,163:
 
One point of interest in the following program is the use of JSON objects to store values. This allows mnemonic names to be used instead of local variables.
<langsyntaxhighlight lang="jq"># Input: { "max": max_run_length,
# "starts": array_of_start_line_values, # of all the maximal runs
# "start_dates": array_of_start_dates # of all the maximal runs
Line 2,097 ⟶ 2,233:
end;
 
process</langsyntaxhighlight>
 
{{out}}
<langsyntaxhighlight lang="sh">$ jq -c -n -R -r -f Text_processing_1.jq readings.txt
[22,590,2]
[24,410,0]
Line 2,106 ⟶ 2,242:
[23,47.3,1]
There is one maximal run of lines with flag<=0.
The maximal run has length 93 and starts at line 5378 and has start date 2004-09-30.</langsyntaxhighlight>
 
=={{header|Julia}}==
<langsyntaxhighlight lang="julia">
using DataFrames
 
Line 2,164 ⟶ 2,300:
maxbaddate = replace("$(df[:Date][maxbadline])", r"T.+$", "")
println("The largest run of bad values is $(maxbadval), on $(maxbaddate) beginning at $(maxbadtime):00 hours.")
</syntaxhighlight>
</lang>
{{output}}
<pre>
Line 2,199 ⟶ 2,335:
 
=={{header|Kotlin}}==
<syntaxhighlight lang="scala">// version 1.2.31
As the link to the full data file is now broken, I've had to confine myself to the 6 lines shown in the task description for testing purposes.
<lang scala>// version 1.2.0
 
import java.io.File
Line 2,250 ⟶ 2,385:
println("\nMaximum run of $maxRun consecutive false readings")
println("ends at line starting with date: $finishLine")
}</langsyntaxhighlight>
 
{{out}}
Abbreviated output:
<pre>
Line: 19911990-0301-3001 Reject: 02 Accept: 2422 Line_tot: 240590.000 Line_avg: 1026.000818
Line: 19911990-0301-3102 Reject: 0 Accept: 24 Line_tot: 565410.000 Line_avg: 2317.542083
Line: 19911990-0301-3103 Reject: 23 0 Accept: 124 Line_tot: 401415.000 Line_avg: 4058.000958
Line: 1991-041990-01-04 Reject: 10 Accept: 2324 Line_tot: 5341800.000 Line_avg: 2375.217000
Line: 19911990-0401-0205 Reject: 0 Accept: 24 Line_tot: 4751130.000 Line_avg: 1947.792083
....
Line: 1991-04-03 Reject: 0 Accept: 24 Line_tot: 335.000 Line_avg: 13.958
Line: 2004-12-27 Reject: 1 Accept: 23 Line_tot: 57.100 Line_avg: 2.483
Line: 2004-12-28 Reject: 1 Accept: 23 Line_tot: 77.800 Line_avg: 3.383
Line: 2004-12-29 Reject: 1 Accept: 23 Line_tot: 56.300 Line_avg: 2.448
Line: 2004-12-30 Reject: 1 Accept: 23 Line_tot: 65.300 Line_avg: 2.839
Line: 2004-12-31 Reject: 1 Accept: 23 Line_tot: 47.300 Line_avg: 2.057
 
File = readings.txt
Total = 21891358393.000400
Readings = 120129403
Average = 1810.242497
 
Maximum run of 24589 consecutive false readings
ends at line starting with date: 19911993-0403-0105
</pre>
 
=={{header|Lua}}==
<langsyntaxhighlight Lualang="lua">filename = "readings.txt"
io.input( filename )
 
Line 2,319 ⟶ 2,460:
print( string.format( "Readings: %d", file_lines ) )
print( string.format( "Average: %f", file_sum/file_cnt_data ) )
print( string.format( "Maximum %d consecutive false readings starting at %s.", max_rejected, max_rejected_date ) )</langsyntaxhighlight>
<pre>Output:
File: readings.txt
Line 2,327 ⟶ 2,468:
Maximum 589 consecutive false readings starting at 1993-02-09.</pre>
 
=={{header|Mathematica}}/{{header|Wolfram Language}}==
<langsyntaxhighlight Mathematicalang="mathematica">FileName = "Readings.txt"; data = Import[FileName,"TSV"];
 
Scan[(a=Position[#[[3;;All;;2]],1];
Print["Line:",#[[1]] ,"\tReject:", 24 - Length[a], "\t Accept:", Length[a], "\tLine_tot:",
Line 2,343 ⟶ 2,483:
Print["\nFile(s) : ",FileName,"\nTotal : ",AccountingForm@GlobalSum,"\nReadings : ",Nb,
"\nAverage : ",GlobalSum/Nb,"\n\nMaximum run(s) of ",MaxRunRecorded,
" consecutive false readings ends at line starting with date(s):",MaxRunTime]</langsyntaxhighlight>
 
<pre>Line:1990-01-01 Reject:2 Accept:22 Line_tot:590. Line_avg:26.8182
Line 2,361 ⟶ 2,501:
=={{header|Nim}}==
{{trans|Python}}
<langsyntaxhighlight lang="nim">import os, sequtils, strutils, sequtilsstrformat
 
var
nodata = 0
nodataMax = -1
nodataMaxLine: seq[string] = @[]
 
totFile = 0.0
Line 2,372 ⟶ 2,512:
 
for filename in commandLineParams():
varfor fline =in open(filename).lines:
for line in f.lines:
var
totLine = 0.0
numLine = 0
fielddata: = line.split()seq[float]
dateflags: = fieldseq[0int]
 
data: seq[float] = @[]
let flags: seq[int]fields = @[]line.split()
let date = fields[0]
 
for i, ffield in fieldfields[1 .. -^1]:
if i mod 2 == 0: data.add parseFloat(ffield)
else: flags.add parseInt(ffield)
 
for datum, flag in items(zip(data, flags)).items:
if flag < 1:
inc nodata
Line 2,402 ⟶ 2,542:
numFile += numLine
 
echolet "Line:average $#= if Reject:numLine $#> Accept0: $#totLine / LineTot: $#float(numLine) LineAvgelse: $#"0.0
echo &"Line: .format({date,} Reject: {data.len - numLine,:2} Accept: {numLine:2} ",
&"LineTot: formatFloat({totLine, precision =:6.2f} 0),LineAvg: formatFloat({average:4.2f}"
(if numLine > 0: totLine / float(numLine) else: 0.0), precision = 0))
 
echo()
echo &"""File(s) = {commandLineParams().join(" ")}"""
echo &"Total = {totFile:.2f}"
echo &"Readings = {numFile}"
echo &"Average = {totFile / float(numFile):.2f}"
echo ""
echo &"Maximum run(s) of {nodataMax} consecutive false readings ",
echo "File(s) = ", commandLineParams().join(" ")
&"""ends at line starting with date(s): {nodataMaxLine.join(" ")}."""</syntaxhighlight>
echo "Total = ", formatFloat(totFile, precision = 0)
 
echo "Readings = ", numFile
{{out}}
echo "Average = ", formatFloat(totFile / float(numFile), precision = 0)
<pre>$ ./textproc1 readings.txt | tail
echo ""
Line: 2004-12-29 Reject: 1 Accept: 23 LineTot: 56.30 LineAvg: 2.45
echo "Maximum run(s) of ", nodataMax, " consecutive false readings ends at line starting with date(s): ", nodataMaxLine.join(" ")</lang>
Line: 2004-12-30 Reject: 1 Accept: 23 LineTot: 65.30 LineAvg: 2.84
Output:
Line: 2004-12-31 Reject: 1 Accept: 23 LineTot: 47.30 LineAvg: 2.06
<pre>$ ./textproc1 readings.txt|tail
Line: 2004-12-29 Reject: 1 Accept: 23 LineTot: 56.3 LineAvg: 2.44783
Line: 2004-12-30 Reject: 1 Accept: 23 LineTot: 65.3 LineAvg: 2.83913
Line: 2004-12-31 Reject: 1 Accept: 23 LineTot: 47.3 LineAvg: 2.05652
 
File(s) = readings.txt
Total = 11358393.35839e+0640
Readings = 129403
Average = 10.497450
 
Maximum run(s) of 589 consecutive false readings ends at line starting with date(s): 1993-03-05.</pre>
 
=={{header|OCaml}}==
<langsyntaxhighlight lang="ocaml">let input_line ic =
try Some(input_line ic)
with End_of_file -> None
Line 2,494 ⟶ 2,635:
Printf.printf "Maximum run(s) of %d consecutive false readings \
ends at line starting with date(s): %s\n"
nodata_max (String.concat ", " nodata_maxline);</langsyntaxhighlight>
 
=={{header|Perl}}==
===An AWK-like solution===
<langsyntaxhighlight lang="perl">use strict;
use warnings;
 
Line 2,556 ⟶ 2,697:
printf "\nMaximum run(s) of %i consecutive false readings ends at line starting with date(s): %s\n",
$nodata_max, $nodata_maxline;</langsyntaxhighlight>
{{out|Sample output}}
<pre>bash$ perl -f readings.pl readings.txt | tail
Line 2,572 ⟶ 2,713:
 
===An object-oriented solution===
<langsyntaxhighlight lang="perl">use strict;
use warnings;
 
Line 2,686 ⟶ 2,827:
$parser->_push_bad_range_if_necessary
}
}</langsyntaxhighlight>
{{out|Sample output}}
<pre>$ perl readings.pl < readings.txt | tail
Line 2,702 ⟶ 2,843:
$</pre>
 
=={{header|Perl 6Phix}}==
<!--<syntaxhighlight lang="phix">(phixonline)-->
<lang perl6>my @gaps;
<span style="color: #000080;font-style:italic;">-- demo\rosetta\TextProcessing1.exw</span>
my $previous = 'valid';
<span style="color: #008080;">with</span> <span style="color: #008080;">javascript_semantics</span> <span style="color: #000080;font-style:italic;">-- (include version/first of next three lines only)</span>
 
<span style="color: #008080;">include</span> <span style="color: #000000;">readings</span><span style="color: #0000FF;">.</span><span style="color: #000000;">e</span> <span style="color: #000080;font-style:italic;">-- global constant lines, or:
for $*IN.lines -> $line {
--assert(write_lines("readings.txt",lines)!=-1) -- first run, then:
my ($date, @readings) = split /\s+/, $line;
--constant lines = read_lines("readings.txt")</span>
my @valid;
my $hour = 0;
<span style="color: #008080;">include</span> <span style="color: #000000;">builtins</span><span style="color: #0000FF;">\</span><span style="color: #004080;">timedate</span><span style="color: #0000FF;">.</span><span style="color: #000000;">e</span>
for @readings -> $reading, $flag {
if $flag > 0 {
<span style="color: #004080;">integer</span> <span style="color: #000000;">count</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">0</span><span style="color: #0000FF;">,</span>
@valid.push($reading);
<span style="color: #000000;">max_count</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">0</span><span style="color: #0000FF;">,</span>
if $previous eq 'invalid' {
<span style="color: #000000;">ntot</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">0</span>
@gaps[*-1]{'end'} = "$date $hour:00";
<span style="color: #004080;">atom</span> <span style="color: #000000;">readtot</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">0</span>
$previous = 'valid';
<span style="color: #004080;">timedate</span> <span style="color: #000000;">run_start</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">max_start</span>
}
}
<span style="color: #008080;">procedure</span> <span style="color: #000000;">end_bad_run</span><span style="color: #0000FF;">()</span>
else
<span style="color: #008080;">if</span> <span style="color: #000000;">count</span> <span style="color: #008080;">then</span>
{
<span style="color: #008080;">if</span> <span style="color: #000000;">count</span><span style="color: #0000FF;">></span><span style="color: #000000;">max_count</span> <span style="color: #008080;">then</span>
if $previous eq 'valid' {
<span style="color: #000000;">max_count</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">count</span>
@gaps.push( {start => "$date $hour:00"} );
<span style="color: #000000;">max_start</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">run_start</span>
}
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
@gaps[*-1]{'count'}++;
<span style="color: #000000;">count</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">0</span>
$previous = 'invalid';
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
}
<span style="color: #008080;">end</span> <span style="color: #008080;">procedure</span>
$hour++;
}
<span style="color: #008080;">for</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">=</span><span style="color: #000000;">1</span> <span style="color: #008080;">to</span> <span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">lines</span><span style="color: #0000FF;">)</span> <span style="color: #008080;">do</span>
say "$date: { ( +@valid ?? ( ( [+] @valid ) / +@valid ).fmt("%.3f") !! 0 ).fmt("%8s") }",
<span style="color: #004080;">sequence</span> <span style="color: #000000;">oneline</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">split</span><span style="color: #0000FF;">(</span><span style="color: #000000;">lines</span><span style="color: #0000FF;">[</span><span style="color: #000000;">i</span><span style="color: #0000FF;">],</span><span style="color: #008000;">'\t'</span><span style="color: #0000FF;">),</span> <span style="color: #000000;">r</span>
" mean from { (+@valid).fmt("%2s") } valid.";
<span style="color: #008080;">if</span> <span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">oneline</span><span style="color: #0000FF;">)!=</span><span style="color: #000000;">49</span> <span style="color: #008080;">then</span>
};
<span style="color: #0000FF;">?</span><span style="color: #008000;">"bad line (length!=49)"</span>
 
<span style="color: #008080;">else</span>
my $longest = @gaps.sort({-$^a<count>})[0];
<span style="color: #000000;">r</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">parse_date_string</span><span style="color: #0000FF;">(</span><span style="color: #000000;">oneline</span><span style="color: #0000FF;">[</span><span style="color: #000000;">1</span><span style="color: #0000FF;">],{</span><span style="color: #008000;">"YYYY-MM-DD"</span><span style="color: #0000FF;">})</span>
 
<span style="color: #008080;">if</span> <span style="color: #008080;">not</span> <span style="color: #004080;">timedate</span><span style="color: #0000FF;">(</span><span style="color: #000000;">r</span><span style="color: #0000FF;">)</span> <span style="color: #008080;">then</span>
say "Longest period of invalid readings was {$longest<count>} hours,\n",
<span style="color: #0000FF;">?{</span><span style="color: #008000;">"bad date"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">oneline</span><span style="color: #0000FF;">[</span><span style="color: #000000;">1</span><span style="color: #0000FF;">]}</span>
"from {$longest<start>} till {$longest<end>}."</lang>
<span style="color: #008080;">else</span>
<span style="color: #004080;">timedate</span> <span style="color: #000000;">td</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">r</span>
<span style="color: #004080;">integer</span> <span style="color: #000000;">rejects</span><span style="color: #0000FF;">=</span><span style="color: #000000;">0</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">accepts</span><span style="color: #0000FF;">=</span><span style="color: #000000;">0</span>
<span style="color: #004080;">atom</span> <span style="color: #000000;">readsum</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">0</span>
<span style="color: #008080;">for</span> <span style="color: #000000;">j</span><span style="color: #0000FF;">=</span><span style="color: #000000;">2</span> <span style="color: #008080;">to</span> <span style="color: #000000;">48</span> <span style="color: #008080;">by</span> <span style="color: #000000;">2</span> <span style="color: #008080;">do</span>
<span style="color: #000000;">r</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">scanf</span><span style="color: #0000FF;">(</span><span style="color: #000000;">oneline</span><span style="color: #0000FF;">[</span><span style="color: #000000;">j</span><span style="color: #0000FF;">],</span><span style="color: #008000;">"%f"</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">if</span> <span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">r</span><span style="color: #0000FF;">)!=</span><span style="color: #000000;">1</span> <span style="color: #008080;">then</span>
<span style="color: #0000FF;">?{</span><span style="color: #008000;">"error scanning"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">oneline</span><span style="color: #0000FF;">[</span><span style="color: #000000;">j</span><span style="color: #0000FF;">]}</span>
<span style="color: #000000;">rejects</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">1</span>
<span style="color: #008080;">else</span>
<span style="color: #004080;">atom</span> <span style="color: #000000;">reading</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">r</span><span style="color: #0000FF;">[</span><span style="color: #000000;">1</span><span style="color: #0000FF;">][</span><span style="color: #000000;">1</span><span style="color: #0000FF;">]</span>
<span style="color: #000000;">r</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">scanf</span><span style="color: #0000FF;">(</span><span style="color: #000000;">oneline</span><span style="color: #0000FF;">[</span><span style="color: #000000;">j</span><span style="color: #0000FF;">+</span><span style="color: #000000;">1</span><span style="color: #0000FF;">],</span><span style="color: #008000;">"%d"</span><span style="color: #0000FF;">)</span>
<span style="color: #008080;">if</span> <span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">r</span><span style="color: #0000FF;">)!=</span><span style="color: #000000;">1</span> <span style="color: #008080;">then</span>
<span style="color: #0000FF;">?{</span><span style="color: #008000;">"error scanning"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">oneline</span><span style="color: #0000FF;">[</span><span style="color: #000000;">j</span><span style="color: #0000FF;">+</span><span style="color: #000000;">1</span><span style="color: #0000FF;">]}</span>
<span style="color: #000000;">rejects</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">1</span>
<span style="color: #008080;">else</span>
<span style="color: #004080;">integer</span> <span style="color: #000000;">flag</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">r</span><span style="color: #0000FF;">[</span><span style="color: #000000;">1</span><span style="color: #0000FF;">][</span><span style="color: #000000;">1</span><span style="color: #0000FF;">]</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">flag</span><span style="color: #0000FF;"><=</span><span style="color: #000000;">0</span> <span style="color: #008080;">then</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">count</span><span style="color: #0000FF;">=</span><span style="color: #000000;">0</span> <span style="color: #008080;">then</span>
<span style="color: #000000;">run_start</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">td</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #000000;">count</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">1</span>
<span style="color: #000000;">rejects</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">1</span>
<span style="color: #008080;">else</span>
<span style="color: #000000;">end_bad_run</span><span style="color: #0000FF;">()</span>
<span style="color: #000000;">accepts</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">1</span>
<span style="color: #000000;">readsum</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">reading</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
<span style="color: #000000;">readtot</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">readsum</span>
<span style="color: #000000;">ntot</span> <span style="color: #0000FF;">+=</span> <span style="color: #000000;">accepts</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">i</span><span style="color: #0000FF;">>=</span><span style="color: #7060A8;">length</span><span style="color: #0000FF;">(</span><span style="color: #000000;">lines</span><span style="color: #0000FF;">)-</span><span style="color: #000000;">2</span> <span style="color: #008080;">then</span>
<span style="color: #004080;">string</span> <span style="color: #000000;">average</span> <span style="color: #0000FF;">=</span> <span style="color: #008080;">iff</span><span style="color: #0000FF;">(</span><span style="color: #000000;">accepts</span><span style="color: #0000FF;">=</span><span style="color: #000000;">0</span><span style="color: #0000FF;">?</span><span style="color: #008000;">"N/A"</span><span style="color: #0000FF;">:</span><span style="color: #7060A8;">sprintf</span><span style="color: #0000FF;">(</span><span style="color: #008000;">"%6.3f"</span><span style="color: #0000FF;">,</span><span style="color: #000000;">readsum</span><span style="color: #0000FF;">/</span><span style="color: #000000;">accepts</span><span style="color: #0000FF;">))</span>
<span style="color: #7060A8;">printf</span><span style="color: #0000FF;">(</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"Date: %s, Rejects: %2d, Accepts: %2d, Line total: %7.3f, Average %s\n"</span><span style="color: #0000FF;">,</span>
<span style="color: #0000FF;">{</span><span style="color: #7060A8;">format_timedate</span><span style="color: #0000FF;">(</span><span style="color: #000000;">td</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"DD/MM/YYYY"</span><span style="color: #0000FF;">),</span><span style="color: #000000;">rejects</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">accepts</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">readsum</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">average</span><span style="color: #0000FF;">})</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">for</span>
<span style="color: #7060A8;">printf</span><span style="color: #0000FF;">(</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"Average: %.3f (of %d readings)\n"</span><span style="color: #0000FF;">,{</span><span style="color: #000000;">readtot</span><span style="color: #0000FF;">/</span><span style="color: #000000;">ntot</span><span style="color: #0000FF;">,</span><span style="color: #000000;">ntot</span><span style="color: #0000FF;">})</span>
<span style="color: #000000;">end_bad_run</span><span style="color: #0000FF;">()</span>
<span style="color: #008080;">if</span> <span style="color: #000000;">max_count</span> <span style="color: #008080;">then</span>
<span style="color: #7060A8;">printf</span><span style="color: #0000FF;">(</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"Maximum run of %d consecutive false readings starting: %s\n"</span><span style="color: #0000FF;">,</span>
<span style="color: #0000FF;">{</span><span style="color: #000000;">max_count</span><span style="color: #0000FF;">,</span><span style="color: #7060A8;">format_timedate</span><span style="color: #0000FF;">(</span><span style="color: #000000;">max_start</span><span style="color: #0000FF;">,</span><span style="color: #008000;">"DD/MM/YYYY"</span><span style="color: #0000FF;">)})</span>
<span style="color: #008080;">end</span> <span style="color: #008080;">if</span>
<span style="color: #0000FF;">?</span><span style="color: #008000;">"done"</span>
<span style="color: #0000FF;">{}</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">wait_key</span><span style="color: #0000FF;">()</span>
<!--</syntaxhighlight>-->
{{out}}
<pre>
Date: 29/12/2004, Rejects: 1, Accepts: 23, Line total: 56.300, Average 2.448
1990-01-01: 26.818 mean from 22 valid.
Date: 30/12/2004, Rejects: 1, Accepts: 23, Line total: 65.300, Average 2.839
1990-01-02: 17.083 mean from 24 valid.
Date: 31/12/2004, Rejects: 1, Accepts: 23, Line total: 47.300, Average 2.057
1990-01-03: 58.958 mean from 24 valid.
Average: 10.497 (of 129403 readings)
1990-01-04: 75.000 mean from 24 valid.
Maximum run of 589 consecutive false readings starting: 09/02/1993
1990-01-05: 47.083 mean from 24 valid.
...
(many lines omitted)
...
2004-12-27: 2.483 mean from 23 valid.
2004-12-28: 3.383 mean from 23 valid.
2004-12-29: 2.448 mean from 23 valid.
2004-12-30: 2.839 mean from 23 valid.
2004-12-31: 2.057 mean from 23 valid.
Longest period of invalid readings was 589 hours,
from 1993-02-09 1:00 till 1993-03-05 14:00.
</pre>
 
=={{header|PhixPicat}}==
{{trans|Ruby}}
As the link to the data file is broken, this is limited to the 6 lines shown in the task description for testing purposes.<br>
<syntaxhighlight lang="picat">go =>
(first constant shown in a smaller font, it actually fits at 4px but...)
File = "readings.txt",
<pre style="font-size: 6px">
Total = new_map([num_readings=0,num_good_readings=0,sum_readings=0.0]),
constant data="""
InvalidCount = 0,
1991-03-30 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1
MaxInvalidCount = 0,
1991-03-31 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 10.000 1 20.000 1 20.000 1 20.000 1 35.000 1 50.000 1 60.000 1 40.000 1 30.000 1 30.000 1 30.000 1 25.000 1 20.000 1 20.000 1 20.000 1 20.000 1 20.000 1 35.000 1
InvalidRunEnd = "",
1991-03-31 40.000 1 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2 0.000 -2
1991-04-01 0.000 -2 13.000 1 16.000 1 21.000 1 24.000 1 22.000 1 20.000 1 18.000 1 29.000 1 44.000 1 50.000 1 43.000 1 38.000 1 27.000 1 27.000 1 24.000 1 23.000 1 18.000 1 12.000 1 13.000 1 14.000 1 15.000 1 13.000 1 10.000 1
1991-04-02 8.000 1 9.000 1 11.000 1 12.000 1 12.000 1 12.000 1 27.000 1 26.000 1 27.000 1 33.000 1 32.000 1 31.000 1 29.000 1 31.000 1 25.000 1 25.000 1 24.000 1 21.000 1 17.000 1 14.000 1 15.000 1 12.000 1 12.000 1 10.000 1
1991-04-03 10.000 1 9.000 1 10.000 1 10.000 1 9.000 1 10.000 1 15.000 1 24.000 1 28.000 1 24.000 1 18.000 1 14.000 1 12.000 1 13.000 1 14.000 1 15.000 1 14.000 1 15.000 1 13.000 1 13.000 1 13.000 1 12.000 1 10.000 1 10.000 1"""
</pre>
<lang Phix>constant lines = split(data,'\n')
 
Id = 0,
include builtins\timedate.e
foreach(Line in read_file_lines(File))
Id := Id + 1,
NumReadings = 0,
NumGoodReadings = 0,
SumReadings = 0,
 
Fields = Line.split,
integer count = 0,
Rec = Fields.tail.map(to_float),
max_count = 0,
foreach([Reading,Flag] in chunks_of(Rec,2))
ntot = 0
NumReadings := NumReadings + 1,
atom readtot = 0
if Flag > 0 then
timedate run_start, max_start
NumGoodReadings := NumGoodReadings + 1,
SumReadings := SumReadings + Reading,
InvalidCount := 0
else
InvalidCount := InvalidCount + 1,
if InvalidCount > MaxInvalidCount then
MaxInvalidCount := InvalidCount,
InvalidRunEnd := Fields[1]
end
end
end,
 
Total.put(num_readings,Total.get(num_readings) + NumReadings),
procedure end_bad_run()
Total.put(num_good_readings,Total.get(num_good_readings) + NumGoodReadings),
if count then
Total.put(sum_readings,Total.get(sum_readings) + SumReadings),
if count>max_count then
if Id <= 3 max_count = countthen
printf("date:%w accept:%w reject:%w sum:%w\n", Fields[1],NumGoodReadings,
max_start = run_start
NumReadings-NumGoodReadings,
end if
SumReadings)
count = 0
end if
end,
end procedure
nl,
printf("readings: %d good readings: %d sum: %0.3f avg: %0.3f\n",Total.get(num_readings),
Total.get(num_good_readings),
Total.get(sum_readings),
Total.get(sum_readings) / Total.get(num_good_readings)),
nl,
println(maxInvalidCount=MaxInvalidCount),
println(invalidRunEnd=InvalidRunEnd),
 
nl.</syntaxhighlight>
for i=1 to length(lines) do
sequence oneline = split(lines[i],no_empty:=true), r
if length(oneline)!=49 then
?"bad line (length!=49)"
else
r = parse_date_string(oneline[1],{"YYYY-MM-DD"})
if not timedate(r) then
?{"bad date",oneline[1]}
else
timedate td = r
integer rejects=0, accepts=0
atom readsum = 0
for j=2 to 48 by 2 do
r = scanf(oneline[j],"%f")
if length(r)!=1 then
?{"error scanning",oneline[j]}
rejects += 1
else
atom reading = r[1][1]
r = scanf(oneline[j+1],"%d")
if length(r)!=1 then
?{"error scanning",oneline[j+1]}
rejects += 1
else
integer flag = r[1][1]
if flag<0 then
if count=0 then
run_start = td
end if
count += 1
rejects += 1
else
end_bad_run()
accepts += 1
readsum += reading
end if
end if
end if
end for
if rejects=0 then
readtot += readsum
ntot += 1
end if
-- readtot += readsum
-- ntot += accepts
printf(1,"Date: %s, Rejects: %2d, Accepts: %2d, Line total: %7.3f, Average %6.3f\n",
{format_timedate(td,"DD/MM/YYYY"),rejects, accepts, readsum, readsum/accepts})
end if
end if
end for
 
printf(1,"Average: %.3f (of %d entirely valid days)\n",{readtot/(24*ntot),ntot})
--printf(1,"Average: %.3f\n",{readtot/ntot})
end_bad_run()
if max_count then
printf(1,"Maximum run of %d consecutive false readings starting: %s\n",
{max_count,format_timedate(max_start,"DD/MM/YYYY")})
end if</lang>
I opted to show an average of entirely good days; the commented out alternative matches Kotlin (18.242).
{{out}}
<pre>
date:1990-01-01 accept:22 reject:2 sum:590.0
Date: 30/03/1991, Rejects: 0, Accepts: 24, Line total: 240.000, Average 10.000
date:1990-01-02 accept:24 reject:0 sum:410.0
Date: 31/03/1991, Rejects: 0, Accepts: 24, Line total: 565.000, Average 23.542
date:1990-01-03 accept:24 reject:0 sum:1415.0
Date: 31/03/1991, Rejects: 23, Accepts: 1, Line total: 40.000, Average 40.000
 
Date: 01/04/1991, Rejects: 1, Accepts: 23, Line total: 534.000, Average 23.217
readings: 131304 good readings: 129403 sum: 1358393.400 avg: 10.497
Date: 02/04/1991, Rejects: 0, Accepts: 24, Line total: 475.000, Average 19.792
 
Date: 03/04/1991, Rejects: 0, Accepts: 24, Line total: 335.000, Average 13.958
maxInvalidCount = 589
Average: 16.823 (of 4 entirely valid days)
invalidRunEnd = 1993-03-05</pre>
Maximum run of 24 consecutive false readings starting: 31/03/1991
 
</pre>
 
=={{header|PicoLisp}}==
{{trans|AWK}}
Put the following into an executable file "readings":
<langsyntaxhighlight PicoLisplang="picolisp">#!/usr/bin/picolisp /usr/lib/picolisp/lib.l
 
(let (NoData 0 NoDataMax -1 NoDataMaxline "!" TotFile 0 NumFile 0)
Line 2,903 ⟶ 3,048:
" consecutive false readings ends at line starting with date(s): " NoDataMaxline ) ) )
 
(bye)</langsyntaxhighlight>
Then it can be called as
<pre>$ ./readings readings.txt |tail
Line 2,919 ⟶ 3,064:
 
=={{header|PL/I}}==
<langsyntaxhighlight lang="pli">text1: procedure options (main); /* 13 May 2010 */
 
declare line character (2000) varying;
Line 2,972 ⟶ 3,117:
finish_up:
end text1;</langsyntaxhighlight>
 
=={{header|PowerShell}}==
<syntaxhighlight lang="powershell">$file = '.\readings.txt'
$lines = Get-Content $file # $args[0]
$valid = $true
$startDate = $currStart = $endDate = ''
$startHour = $endHour = $currHour = $max = $currMax = $total = $readings = 0
$task = @()
foreach ($var in $lines) {
$date, $rest = [regex]::Split($var,'\s+')
$reject = $accept = $sum = $cnt = 0
while ($rest) {
$cnt += 1
[Double]$val, [Double]$flag, $rest = $rest
if (0 -lt $flag) {
$currMax = 0
$sum += $val
$accept += 1
} else {
if (0 -eq $currMax) {
$currStart = $date
$currHour = $cnt
}
$currMax += 1
$reject += 1
if ($max -lt $currMax) {
$startDate, $endDate = $currStart, $date
$startHour, $endHour = $currHour, $cnt
$max = $currMax
}
}
}
$readings += $accept
$total += $sum
$average = if (0 -lt $accept) {$sum/$accept} else {0}
$task += [PSCustomObject]@{
'Line' = $date
'Reject' = $reject
'Accept' = $accept
'Sum' = $sum.ToString("N")
'Average' = $average.ToString("N3")
}
$valid = 0 -eq $reject
}
$task | Select -Last 3
$average = $total/$readings
"File(s) = $file"
"Total = {0}" -f $total.ToString("N")
"Readings = $readings"
"Average = {0}" -f $average.ToString("N3")
""
"Maximum run(s) of $max consecutive false readings."
if (0 -lt $max) {
"Consecutive false readings starts at line starting with date $startDate at hour {0:0#}:00." -f $startHour
"Consecutive false readings ends at line starting with date $endDate at hour {0:0#}:00." -f $endHour
}</syntaxhighlight>
<pre>Line : 2004-12-29
Reject : 1
Accept : 23
Sum : 56.30
Average : 2.448
 
Line : 2004-12-30
Reject : 1
Accept : 23
Sum : 65.30
Average : 2.839
 
Line : 2004-12-31
Reject : 1
Accept : 23
Sum : 47.30
Average : 2.057
 
 
File(s) = .\readings.txt
Total = 1,358,393.40
Readings = 129403
Average = 10.497
 
Maximum run(s) of 589 consecutive false readings.
Consecutive false readings starts at line starting with date 1993-02-09 at hour 02:00.
Consecutive false readings ends at line starting with date 1993-03-05 at hour 14:00.</pre>
 
=={{header|PureBasic}}==
<langsyntaxhighlight PureBasiclang="purebasic">#TASK="Text processing/1"
Define File$, InLine$, Part$, i, Out$, ErrEnds$, Errcnt, ErrMax
Define lsum.d, tsum.d, rejects, val.d, readings
Line 3,021 ⟶ 3,249:
;
Print("Press ENTER to exit"): Input()
EndIf</langsyntaxhighlight>
{{out|Sample output}}
<pre>...
Line 3,038 ⟶ 3,266:
 
=={{header|Python}}==
<langsyntaxhighlight lang="python">import fileinput
import sys
 
Line 3,093 ⟶ 3,321:
 
print "\nMaximum run(s) of %i consecutive false readings ends at line starting with date(s): %s" % (
nodata_max, ", ".join(nodata_maxline))</langsyntaxhighlight>
{{out|Sample output}}
<pre>bash$ /cygdrive/c/Python26/python readings.py readings.txt|tail
Line 3,109 ⟶ 3,337:
 
=={{header|R}}==
<langsyntaxhighlight Rlang="r">#Read in data from file
dfr <- read.delim("readings.txt")
#Calculate daily means
Line 3,117 ⟶ 3,345:
#Calculate time between good measurements
times <- strptime(dfr[1,1], "%Y-%m-%d", tz="GMT") + 3600*seq(1,24*nrow(dfr),1)
hours.between.good.measurements <- diff(times[t(flags)])/3600</langsyntaxhighlight>
 
=={{header|Racket}}==
<langsyntaxhighlight lang="racket">#lang racket
;; Use SRFI 48 to make %n.nf formats convenient.
(require (prefix-in srfi/48: srfi/48)) ; SRFI 48: Intermediate Format Strings
Line 3,173 ⟶ 3,401:
(unless (zero? N) (srfi/48:format #t "Average = ~10,3F~%" (/ sum N)))
(srfi/48:format #t "~%Maximum run(s) of ~a consecutive false readings ends at line starting with date(s): ~a~%"
max-consecutive-false (string-join max-false-tags))))</langsyntaxhighlight>
{{out|Sample run}}
<pre>$ racket 1.rkt readings/readings.txt | tail
Line 3,186 ⟶ 3,414:
 
Maximum run(s) of 589 consecutive false readings ends at line starting with date(s): 1993-03-05</pre>
 
=={{header|Raku}}==
(formerly Perl 6)
<syntaxhighlight lang="raku" line>my @gaps;
my $previous = 'valid';
 
for $*IN.lines -> $line {
my ($date, @readings) = split /\s+/, $line;
my @valid;
my $hour = 0;
for @readings -> $reading, $flag {
if $flag > 0 {
@valid.push($reading);
if $previous eq 'invalid' {
@gaps[*-1]{'end'} = "$date $hour:00";
$previous = 'valid';
}
}
else
{
if $previous eq 'valid' {
@gaps.push( {start => "$date $hour:00"} );
}
@gaps[*-1]{'count'}++;
$previous = 'invalid';
}
$hour++;
}
say "$date: { ( +@valid ?? ( ( [+] @valid ) / +@valid ).fmt("%.3f") !! 0 ).fmt("%8s") }",
" mean from { (+@valid).fmt("%2s") } valid.";
};
 
my $longest = @gaps.sort({-$^a<count>})[0];
 
say "Longest period of invalid readings was {$longest<count>} hours,\n",
"from {$longest<start>} till {$longest<end>}."</syntaxhighlight>
{{out}}
<pre>
1990-01-01: 26.818 mean from 22 valid.
1990-01-02: 17.083 mean from 24 valid.
1990-01-03: 58.958 mean from 24 valid.
1990-01-04: 75.000 mean from 24 valid.
1990-01-05: 47.083 mean from 24 valid.
...
(many lines omitted)
...
2004-12-27: 2.483 mean from 23 valid.
2004-12-28: 3.383 mean from 23 valid.
2004-12-29: 2.448 mean from 23 valid.
2004-12-30: 2.839 mean from 23 valid.
2004-12-31: 2.057 mean from 23 valid.
Longest period of invalid readings was 589 hours,
from 1993-02-09 1:00 till 1993-03-05 14:00.
</pre>
 
=={{header|REXX}}==
<langsyntaxhighlight lang="rexx">/*REXX program to process instrument data from a data file. */
numeric digits 20 /*allow for bigger (precision) numbers.*/
ifid='READINGS.TXT' /*the name of the input file. */
Line 3,252 ⟶ 3,534:
do j=e to b by -3; _=insert(',',_,j); end /*j*/; return _
/*────────────────────────────────────────────────────────────────────────────*/
sy: say arg(1); call lineout ofid,arg(1); return</langsyntaxhighlight>
'''output''' &nbsp; when using the default input file:
<pre style="height:40ex">
Line 3,275 ⟶ 3,557:
 
=={{header|Ruby}}==
<langsyntaxhighlight lang="ruby">filename = "readings.txt"
total = { "num_readings" => 0, "num_good_readings" => 0, "sum_readings" => 0.0 }
invalid_count = 0
Line 3,317 ⟶ 3,599:
printf "Average = %.3f\n", total['sum_readings']/total['num_good_readings']
puts ""
puts "Maximum run(s) of #{max_invalid_count} consecutive false readings ends at #{invalid_run_end}"</langsyntaxhighlight>
 
Alternate implementation:
<langsyntaxhighlight lang="ruby">Reading = Struct.new(:date, :value, :flag)
 
DailyReading = Struct.new(:date, :readings) do
Line 3,352 ⟶ 3,634:
puts
puts "Max run of #{worst_streak.count} consecutive false readings from #{worst_streak.first.date} until #{worst_streak.last.date}"
</syntaxhighlight>
</lang>
 
=={{header|Scala}}==
Line 3,358 ⟶ 3,640:
 
A fully functional solution, minus the fact that it uses iterators:
<langsyntaxhighlight lang="scala">object DataMunging {
import scala.io.Source
Line 3,415 ⟶ 3,697:
println(report format (files mkString " ", totalSum, totalSize, totalSum / totalSize, invalidCount, startDate))
}
}</langsyntaxhighlight>
A quick&dirty solution:
<langsyntaxhighlight lang="scala">object AltDataMunging {
def main(args: Array[String]) {
var totalSum = 0.0
Line 3,458 ⟶ 3,740:
println(report format (files mkString " ", totalSum, totalSize, totalSum / totalSize, maxInvalidCount, maxInvalidDate))
}
}</langsyntaxhighlight>
Last few lines of the sample output (either version):
<pre>
Line 3,475 ⟶ 3,757:
 
=={{header|Sidef}}==
{{trans|Perl 6Raku}}
<langsyntaxhighlight lang="ruby">var gaps = [];
var previous = :valid;
 
Line 3,483 ⟶ 3,765:
var valid = [];
var hour = 0;
readings.map{.to_n}.each_slice(2, { |slicereading, flag|
var(reading, flag) = slice...;
if (flag > 0) {
valid << reading;
Line 3,508 ⟶ 3,789:
 
say ("Longest period of invalid readings was #{longest{:count}} hours,\n",
"from #{longest{:start}} till #{longest{:end}}.");</langsyntaxhighlight>
{{out}}
<pre>
Line 3,521 ⟶ 3,802:
</pre>
''Output is from the sample of the task.''
 
=={{header|Swift}}==
 
{{trans|Rust}}
 
<syntaxhighlight lang="swift">import Foundation
 
let fmtDbl = { String(format: "%10.3f", $0) }
 
Task.detached {
let formatter = DateFormatter()
 
formatter.dateFormat = "yyyy-MM-dd"
 
let (data, _) = try await URLSession.shared.bytes(from: URL(fileURLWithPath: CommandLine.arguments[1]))
var rowStats = [(Date, Double, Int)]()
var invalidPeriods = 0
var invalidStart: Date?
var sumFile = 0.0
var readings = 0
var longestInvalid = 0
var longestInvalidStart: Date?
var longestInvalidEnd: Date?
 
for try await line in data.lines {
let lineSplit = line.components(separatedBy: "\t")
 
guard !lineSplit.isEmpty, let date = formatter.date(from: lineSplit[0]) else {
fatalError("Invalid date \(lineSplit[0])")
}
 
let data = Array(lineSplit.dropFirst())
let parsed = stride(from: 0, to: data.endIndex, by: 2).map({idx -> (Double, Int) in
let slice = data[idx..<idx+2]
 
return (Double(slice[idx]) ?? 0, Int(slice[idx+1]) ?? 0)
})
 
var sum = 0.0
var numValid = 0
 
for (val, flag) in parsed {
if flag <= 0 {
if invalidStart == nil {
invalidStart = date
}
 
invalidPeriods += 1
} else {
if invalidPeriods > longestInvalid {
longestInvalid = invalidPeriods
longestInvalidStart = invalidStart
longestInvalidEnd = date
}
 
sumFile += val
sum += val
numValid += 1
readings += 1
invalidPeriods = 0
invalidStart = nil
}
}
 
if numValid != 0 {
rowStats.append((date, sum / Double(numValid), parsed.count - numValid))
}
}
 
for stat in rowStats.lazy.reversed().prefix(5) {
print("\(stat.0): Average: \(fmtDbl(stat.1)); Valid Readings: \(24 - stat.2); Invalid Readings: \(stat.2)")
}
 
print("""
 
Sum File: \(fmtDbl(sumFile))
Average: \(fmtDbl(sumFile / Double(readings)))
Readings: \(readings)
Longest Invalid: \(longestInvalid) (\(longestInvalidStart!) - \(longestInvalidEnd!))
""")
 
exit(0)
}
 
dispatchMain()
</syntaxhighlight>
 
{{out}}
 
<pre>2004-12-31 05:00:00 +0000: Average: 2.057; Valid Readings: 23; Invalid Readings: 1
2004-12-30 05:00:00 +0000: Average: 2.839; Valid Readings: 23; Invalid Readings: 1
2004-12-29 05:00:00 +0000: Average: 2.448; Valid Readings: 23; Invalid Readings: 1
2004-12-28 05:00:00 +0000: Average: 3.383; Valid Readings: 23; Invalid Readings: 1
2004-12-27 05:00:00 +0000: Average: 2.483; Valid Readings: 23; Invalid Readings: 1
 
Sum File: 1358393.400
Average: 10.497
Readings: 129403
Longest Invalid: 589 (1993-02-09 05:00:00 +0000 - 1993-03-05 05:00:00 +0000)</pre>
 
=={{header|Tcl}}==
<langsyntaxhighlight lang="tcl">set max_invalid_run 0
set max_invalid_run_end ""
set tot_file 0
Line 3,563 ⟶ 3,943:
puts "Average = [format %.3f [expr {$tot_file / $num_file}]]"
puts ""
puts "Maximum run(s) of $max_invalid_run consecutive false readings ends at $max_invalid_run_end"</langsyntaxhighlight>
 
=={{header|Ursala}}==
Line 3,569 ⟶ 3,949:
and booleans (type <code>%ebXLm</code>) in the parsed data. The same function is used to compute the daily and the
cumulative statistics.
<langsyntaxhighlight Ursalalang="ursala">#import std
#import nat
#import flo
Line 3,589 ⟶ 3,969:
@nmrSPDSL -&~&,leql$^; ^/length ~&zn&-@hrZPF+ rlc both ~&rZ+-
 
main = ^T(daily_stats^lrNCT/~& @mSL 'summary ':,long_run) parsed_data</langsyntaxhighlight>
last few lines of output:
<pre>
Line 3,600 ⟶ 3,980:
 
=={{header|VBScript}}==
<langsyntaxhighlight lang="vb">Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objFile = objFSO.OpenTextFile(objFSO.GetParentFolderName(WScript.ScriptFullName) &_
"\data.txt",1)
Line 3,662 ⟶ 4,042:
WScript.StdOut.WriteLine
objFile.Close
Set objFSO = Nothing</langsyntaxhighlight>
{{Out}}
<pre>
Line 3,678 ⟶ 4,058:
{{trans|AWK}}
Vedit does not have floating point data type, so fixed point calculations are used here.
<langsyntaxhighlight lang="vedit">#50 = Buf_Num // Current edit buffer (source data)
File_Open("output.txt")
#51 = Buf_Num // Edit buffer for output file
Line 3,745 ⟶ 4,125:
IT("Maximum run(s) of ") Num_Ins(#13, LEFT+NOCR)
IT(" consecutive false readings ends at line starting with date(s): ") Reg_Ins(15)
IN</langsyntaxhighlight>
{{out|Sample output}}
<pre>
Line 3,759 ⟶ 4,139:
Maximum run(s) of 589 consecutive false readings ends at line starting with date(s): 1993-03-05
</pre>
 
=={{header|Wren}}==
{{trans|Kotlin}}
{{libheader|Wren-pattern}}
{{libheader|Wren-fmt}}
<syntaxhighlight lang="wren">import "io" for File
import "./pattern" for Pattern
import "./fmt" for Fmt
 
var p = Pattern.new("+1/s")
var fileName = "readings.txt"
var lines = File.read(fileName).trimEnd().split("\r\n")
var f = "Line: $s Reject: $2d Accept: $2d Line_tot: $8.3f Line_avg: $7.3f"
var grandTotal = 0
var readings = 0
var date = ""
var run = 0
var maxRun = -1
var finishLine = ""
for (line in lines) {
var fields = p.splitAll(line)
date = fields[0]
if (fields.count == 49) {
var accept = 0
var total = 0
var i = 1
while (i < fields.count) {
if (Num.fromString(fields[i+1]) >= 1) {
accept = accept + 1
total = total + Num.fromString(fields[i])
if (run > maxRun) {
maxRun = run
finishLine = date
}
run = 0
} else {
run = run + 1
}
i = i + 2
}
grandTotal = grandTotal + total
readings = readings + accept
Fmt.print(f, date, 24-accept, accept, total, total/accept)
} else {
Fmt.print("Line: $s does not have 49 fields and has been ignored", date)
}
}
 
if (run > maxRun) {
maxRun = run
finishLine = date
}
var average = grandTotal / readings
Fmt.print("\nFile = $s", fileName)
Fmt.print("Total = $0.3f", grandTotal)
Fmt.print("Readings = $d", readings)
Fmt.print("Average = $0.3f", average)
Fmt.print("\nMaximum run of $d consecutive false readings", maxRun)
Fmt.print("ends at line starting with date: $s", finishLine)</syntaxhighlight>
 
{{out}}
Abridged output.
<pre>
Line: 1990-01-01 Reject: 2 Accept: 22 Line_tot: 590.000 Line_avg: 26.818
Line: 1990-01-02 Reject: 0 Accept: 24 Line_tot: 410.000 Line_avg: 17.083
Line: 1990-01-03 Reject: 0 Accept: 24 Line_tot: 1415.000 Line_avg: 58.958
Line: 1990-01-04 Reject: 0 Accept: 24 Line_tot: 1800.000 Line_avg: 75.000
Line: 1990-01-05 Reject: 0 Accept: 24 Line_tot: 1130.000 Line_avg: 47.083
...
Line: 2004-12-27 Reject: 1 Accept: 23 Line_tot: 57.100 Line_avg: 2.483
Line: 2004-12-28 Reject: 1 Accept: 23 Line_tot: 77.800 Line_avg: 3.383
Line: 2004-12-29 Reject: 1 Accept: 23 Line_tot: 56.300 Line_avg: 2.448
Line: 2004-12-30 Reject: 1 Accept: 23 Line_tot: 65.300 Line_avg: 2.839
Line: 2004-12-31 Reject: 1 Accept: 23 Line_tot: 47.300 Line_avg: 2.057
 
File = readings.txt
Total = 1358393.400
Readings = 129403
Average = 10.497
 
Maximum run of 589 consecutive false readings
ends at line starting with date: 1993-03-05
</pre>
 
 
{{omit from|Openscad}}
{{omit from|PARI/GP|No real capacity for string manipulation}}
{{omit from|Phix|Sample data missing}}
9,476

edits