|
LiveGraph data visualisation and analysis framework |
|||||||||
PREV CLASS NEXT CLASS | FRAMES NO FRAMES | |||||||||
SUMMARY: NESTED | FIELD | CONSTR | METHOD | DETAIL: FIELD | CONSTR | METHOD |
java.lang.Objectorg.LiveGraph.dataFile.write.DataStreamWriter
public class DataStreamWriter
DataStreamWriter
objects are used for writing files in the LiveGraph file format.
DataStreamWriter
does not extend java.io.Writer
because the structure
of the data being written is different and the making use of the methods published by
the standard API class would be counter-intuitive; however, DataStreamWriter
objects should be used in much the same manner as a normal Writer
in an
application.
The DataStreamWriter
class provides methods for setting up the data file separator,
adding information lines and comments to the data file, defining the number of and the
labels for the data series and, eventually, for writing the data.
Before any data is sent to the writer the data series should be set up with a series of
calls to addDataSeries(String)
. Once a dataset is written to the stream, no
more data series may be added.
A dataset is written by a series of calls to one of the setDataValue(...)
methods. Calls to those methods do not cause any data to be written. Instead, the values
are associated with the appropriate data series and cached. In order to actually write the
data to the underlying stream the method writeDataSet()
must be invoked. It flushes
the cache to the data stream and prepares for the processing of the next dataset.
In order to allow for concise code when using this class in applications, no methods
of DataStreamWriter
throw any I/O exceptions. If an IOException
is
thrown by the underlying stream, it is immediately caught by this class. In order to
allow the application to nevertheless access and control the error handling, the methods
hadIOException()
, getIOException()
and resetIOException()
are
provided.
An example of how to use this class can be found in
LiveGraphDemo
.
Here is a formal description of the file format produced by this class:
The LiveGraph API reads and stores data in text-based data files. The file format is based on the widely used comma-separated-values (CSV) format. LiveGraph′s file format was defined in such a way that a standard CSV file will be accepted and correctly parsed by the application (except that the very first data line might be interpreted as column headings - see below).
The format definition is as follows:
1. File is character and line based.
LiveGraph data files are text-files (i.e. not binary files). Files are read (written) on
a line-by-line basis. Only after a complete line was read and parsed (or written) will
the next line be considered.
2. Empty lines are ignored.
Any empty line or a line containing only white spaces is ignored without any further
consequences.
3. Data values separator definition line.
The first non-empty line in a LiveGraph data file may contain an optional data
values separator definition. A data values separator is a string which will separate data
values in data lines.
A data values separator definition line must start and finish with the tag
"##". The entire string between the opening "##"
and the closing "##" will be the treated as the separator. For instance,
the line "##(*)##" defines the data values separator
"(*)".
A data values separator definition may not appear anywhere else than on the first non-empty
line of the data file.
If the data values separator definition is omitted the default data values separator will be
the string "," (comma).
4. Comment lines.
Any line where the first non-whitespace character is "#" (except for
the data values separator definition line) is treated as a comment and is ignored. Note that
no comments may be placed before the optional data values separator definition line.
5. File information and description lines.
Any line where the first non-whitespace character is "@" is treated as
a file information or description line. A file information line does not have any effect on
the interpretation of the data contained in the file; however, it may be used by a
processing application to provide information to the end-user.
6. Data series labels line.
The first non-empty line in a data file which is not a data separator definition line or a
comment line or a file information line is treated as data series labels line. This line
defines the number and the labels of the data columns in the file. The line is split in
tokens using the data values separator. The number of tokens defines the number of data
columns in the file and the tokens define the labels of the columns. Note that the labels
might be empty strings. For example:
##;## @Example 1 ID;Age;;Height . . .
@Example 2 ,ID;Height,Age,weight, . . .
In example 1 the data separator is defined to be "" (semicolon).
4 data series are defined here: "ID", "Age",
"" and "Height" (note that the third series
label here is an empty string).
In example 2 no data separator is defined, so the default separator ","
(comma) is used. Note that "" is not a separator in this case. This
gives 5 data series with the following labels: "",
"ID;Height", "Age", "weight"
and "". Note that the first and the last series labels are empty
strings. They are separated from the following (preceding) labels by the data separator.
7. Data lines.
Any non-empty line after the series labels line which is not a comment line or a file
information line is treated as data values line. Data lines contain the actual data. They
are parsed into tokens in the same way as the data series labels line, which means that
some tokens may be empty strings. The LiveGraph API allows any string to be used as a token.
(Note that the plotter application converts each token to a double precision floating point
value; if a token is not a character string representing a valid decimal number, it will be
converted to a not-a-number floating point value. This is interpreted by the plotter as a
gap in the data series.) All data values on the same line are considered to belong to the
same dataset. The data series of each value in a given dataset is determined by comparing
the position index of the corresponding data token in the line to the number of the series
label token in the labels line.
Here is an example data file:
##|## @File info for the user @More info #Comment Seconds|Dead mosquitos|Hungry frogs 1|0|100 600|1000|50 1500|5000|0 #Another comment
Here is another example:
Seconds,Dead mosquitos,Hungry frogs 1,0,100 600,1000,50 1500,5000,0
This product includes software developed by the
LiveGraph project and its contributors.
(http://www.live-graph.org)
Copyright (c) 2007 G. Paperin.
All rights reserved.
File: DataStreamWriter.java
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following terms and conditions are met:
1. Redistributions of source code must retain the above
acknowledgement of the LiveGraph project and its web-site, the above copyright notice,
this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above acknowledgement of the
LiveGraph project and its web-site, the above copyright notice, this list of conditions
and the following disclaimer in the documentation and/or other materials provided with
the distribution.
3. All advertising materials mentioning features or use of this software or any derived
software must display the following acknowledgement:
This product includes software developed by the LiveGraph project and its
contributors.
(http://www.live-graph.org)
4. All advertising materials distributed in form of HTML pages or any other technology
permitting active hyper-links that mention features or use of this software or any
derived software must display the acknowledgment specified in condition 3 of this
agreement, and in addition, include a visible and working hyper-link to the LiveGraph
homepage (http://www.live-graph.org).
THIS SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS, CONTRIBUTORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
Field Summary | |
---|---|
private boolean |
canAddDataSeries
Whether new data series can still be added. |
private boolean |
canChangeSeparator
Whether the data separator can still be changed. |
private int |
currentSeriesIndex
Holds the series index cursor within the current dataset. |
private java.util.Map<java.lang.String,java.lang.String> |
dataCache
Values of the current dataset. |
private java.util.List<java.lang.String> |
dataSeriesLabels
Holds the data series labels. |
private java.io.IOException |
ioException
Raised IOException (if any). |
private java.io.BufferedWriter |
out
Streat writer for printing to the output stream. |
private java.lang.String |
separator
The currently used data values separator. |
Constructor Summary | |
---|---|
DataStreamWriter(java.io.OutputStream os)
Creates a new data writer to write on the specified stream. |
Method Summary | |
---|---|
void |
addDataSeries(java.lang.String label)
Defines a new data series with the specified label for this writer. |
private void |
checkWriteSeparatorDefinition()
If a non-default separator was set it is written to the output stream, unless other data was already written. |
private void |
checkWriteSeriesLabels()
Writes data series label information to the output stream. |
void |
close()
Closes the underlying output stream. |
boolean |
dataSeriesExists(java.lang.String label)
Checks whether this writer knows a data series with the specified label. |
java.lang.String |
getDataValue(int seriesIndex)
Gets the data value which has been previously associated with the specified data series in the current dataset. |
java.lang.String |
getDataValue(java.lang.String seriesLabel)
Gets the data value which has been previously associated with the specified data series in the current dataset. |
java.io.IOException |
getIOException()
Gets the last IOException encountered by this writer. |
boolean |
hadIOException()
Check whether a recent operation caused an IOException . |
void |
resetIOException()
Deletes any internal state concerned with previously encountered IOException s. |
void |
setDataValue(boolean value)
Assigns the specified value to the next data series in the current dataset. |
void |
setDataValue(double value)
Assigns the specified value to the next data series in the current dataset. |
void |
setDataValue(float value)
Assigns the specified value to the next data series in the current dataset. |
void |
setDataValue(int value)
Assigns the specified value to the next data series in the current dataset. |
void |
setDataValue(int seriesIndex,
boolean value)
Assigns the specified value to the data series at the specified index in the current dataset. |
void |
setDataValue(int seriesIndex,
double value)
Assigns the specified value to the data series at the specified index in the current dataset. |
void |
setDataValue(int seriesIndex,
float value)
Assigns the specified value to the data series at the specified index in the current dataset. |
void |
setDataValue(int seriesIndex,
int value)
Assigns the specified value to the data series at the specified index in the current dataset. |
void |
setDataValue(int seriesIndex,
long value)
Assigns the specified value to the data series at the specified index in the current dataset. |
void |
setDataValue(int seriesIndex,
java.lang.String value)
Assigns the specified value to the data series at the specified index in the current dataset. |
void |
setDataValue(long value)
Assigns the specified value to the next data series in the current dataset. |
void |
setDataValue(java.lang.String value)
Assigns the specified value to the next data series in the current dataset. |
void |
setDataValue(java.lang.String seriesLabel,
boolean value)
Assigns the specified value to the specified data series in the current dataset. |
void |
setDataValue(java.lang.String seriesLabel,
double value)
Assigns the specified value to the specified data series in the current dataset. |
void |
setDataValue(java.lang.String seriesLabel,
float value)
Assigns the specified value to the specified data series in the current dataset. |
void |
setDataValue(java.lang.String seriesLabel,
int value)
Assigns the specified value to the specified data series in the current dataset. |
void |
setDataValue(java.lang.String seriesLabel,
long value)
Assigns the specified value to the specified data series in the current dataset. |
void |
setDataValue(java.lang.String seriesLabel,
java.lang.String value)
Assigns the specified value to the specified data series in the current dataset. |
void |
setSeparator(java.lang.String sep)
Sets the separator between data columns and values. |
void |
writeComment(java.lang.String comm)
Writes the specified comment to the output stream. |
void |
writeDataSet()
Writes the current dataset to the output stream. |
void |
writeFileInfo(java.lang.String info)
Writes the specified information or file description line to the output stream. |
Methods inherited from class java.lang.Object |
---|
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait |
Field Detail |
---|
private java.io.BufferedWriter out
private boolean canChangeSeparator
private java.lang.String separator
private boolean canAddDataSeries
private java.util.List<java.lang.String> dataSeriesLabels
private int currentSeriesIndex
private java.util.Map<java.lang.String,java.lang.String> dataCache
private java.io.IOException ioException
Constructor Detail |
---|
public DataStreamWriter(java.io.OutputStream os)
os
- The stream to the the data will be written.Method Detail |
---|
public void close()
setDataValue(...)
-methods are not written yet, they wre written to the stream before it is closed.
Once this method was invoken, no more data can be written.
public void setSeparator(java.lang.String sep)
sep
- The new separator.
java.lang.IllegalStateException
- If the separator cannot be changed because other data was already written.
java.lang.IllegalArgumentException
- If the specified separator is not allowed.DataFormatTools.isValidSeparator(String)
private void checkWriteSeparatorDefinition()
private void checkWriteSeriesLabels()
public void writeComment(java.lang.String comm)
comm
- A comment line.public void writeFileInfo(java.lang.String info)
info
- An information or file description line.public boolean dataSeriesExists(java.lang.String label)
label
- A data series label.
true
if a data series has been defined on this writer,
false
otherwise.public void addDataSeries(java.lang.String label)
label
- Label for the new data series.
java.lang.NullPointerException
- If the label is null
.
java.lang.IllegalStateException
- If no more data series may be defined because datasets
have already been written to the output stream.public void setDataValue(java.lang.String seriesLabel, double value)
seriesLabel
- Label of the series to which value
is to be assigned.value
- A value to include in the current dataset.public void setDataValue(int seriesIndex, double value)
seriesIndex
- Column index of the series to which value
is to be assigned.value
- A value to include in the current dataset.
java.lang.IllegalArgumentException
- If seriesIndex < 0
or if
seriesIndex >= (number of data-series defined for this writer)
.public void setDataValue(double value)
value
- A value to include in the current dataset.
java.lang.IllegalArgumentException
- If there are no more data series defined for this writer.public void setDataValue(java.lang.String seriesLabel, float value)
seriesLabel
- Label of the series to which value
is to be assigned.value
- A value to include in the current dataset.public void setDataValue(int seriesIndex, float value)
seriesIndex
- Column index of the series to which value
is to be assigned.value
- A value to include in the current dataset.
java.lang.IllegalArgumentException
- If seriesIndex < 0
or if
seriesIndex >= (number of data-series defined for this writer)
.public void setDataValue(float value)
value
- A value to include in the current dataset.
java.lang.IllegalArgumentException
- If there are no more data series defined for this writer.public void setDataValue(java.lang.String seriesLabel, long value)
seriesLabel
- Label of the series to which value
is to be assigned.value
- A value to include in the current dataset.public void setDataValue(int seriesIndex, long value)
seriesIndex
- Column index of the series to which value
is to be assigned.value
- A value to include in the current dataset.
java.lang.IllegalArgumentException
- If seriesIndex < 0
or if
seriesIndex >= (number of data-series defined for this writer)
.public void setDataValue(long value)
value
- A value to include in the current dataset.
java.lang.IllegalArgumentException
- If there are no more data series defined for this writer.public void setDataValue(java.lang.String seriesLabel, int value)
seriesLabel
- Label of the series to which value
is to be assigned.value
- A value to include in the current dataset.public void setDataValue(int seriesIndex, int value)
seriesIndex
- Column index of the series to which value
is to be assigned.value
- A value to include in the current dataset.
java.lang.IllegalArgumentException
- If seriesIndex < 0
or if
seriesIndex >= (number of data-series defined for this writer)
.public void setDataValue(int value)
value
- A value to include in the current dataset.
java.lang.IllegalArgumentException
- If there are no more data series defined for this writer.public void setDataValue(java.lang.String seriesLabel, boolean value)
seriesLabel
- Label of the series to which value
is to be assigned.value
- A value to include in the current dataset (true
will be
converted to 1
and false
will be converted to 0
).public void setDataValue(int seriesIndex, boolean value)
seriesIndex
- Column index of the series to which value
is to be assigned.value
- A value to include in the current dataset (true
will be
converted to 1
and false
will be converted to 0
).
java.lang.IllegalArgumentException
- If seriesIndex < 0
or if
seriesIndex >= (number of data-series defined for this writer)
.public void setDataValue(boolean value)
value
- A value to include in the current dataset (true
will be
converted to 1
and false
will be converted to 0
).
java.lang.IllegalArgumentException
- If there are no more data series defined for this writer.public void setDataValue(java.lang.String seriesLabel, java.lang.String value)
seriesLabel
- Label of the series to which value
is to be assigned.value
- A value to include in the current dataset (null
will be
converted to the empty string ""
).public void setDataValue(int seriesIndex, java.lang.String value)
seriesIndex
- Column index of the series to which value
is to be assigned.value
- A value to include in the current dataset (null
will be
converted to the empty string ""
).
java.lang.IllegalArgumentException
- If seriesIndex < 0
or if
seriesIndex >= (number of data-series defined for this writer)
.public void setDataValue(java.lang.String value)
value
- A value to include in the current dataset (null
will be
converted to the empty string ""
).
java.lang.IllegalArgumentException
- If there are no more data series defined for this writer.public java.lang.String getDataValue(java.lang.String seriesLabel)
seriesLabel
- The label of the data series to query.
String
or null
if no value was associated with the specified
data series.public java.lang.String getDataValue(int seriesIndex)
seriesIndex
- Column index of the data series to query.
String
or null
if no value was associated with the specified
data series.public void writeDataSet()
public boolean hadIOException()
IOException
.
true
if an IOException
was encountered after this writer was created or after
the last call to resetIOException()
, false
otherwise.public java.io.IOException getIOException()
IOException
encountered by this writer.
hadIOException()
returns true
- the last IOException
encountered
by this writer, otherwise - null
.public void resetIOException()
IOException
s.
|
LiveGraph data visualisation and analysis framework |
|||||||||
PREV CLASS NEXT CLASS | FRAMES NO FRAMES | |||||||||
SUMMARY: NESTED | FIELD | CONSTR | METHOD | DETAIL: FIELD | CONSTR | METHOD |