Skip to content

Commit

Permalink
update docstring
Browse files Browse the repository at this point in the history
  • Loading branch information
MAfarrag committed Jan 17, 2025
1 parent bc9ae67 commit aef2375
Show file tree
Hide file tree
Showing 3 changed files with 116 additions and 77 deletions.
182 changes: 105 additions & 77 deletions hydrolib/core/dflowfm/tim/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -24,80 +24,92 @@ class TimModel(ParsableFileModel):
"""Class representing a tim (*.tim) file.
Attributes:
-----------
serializer_config : TimSerializerConfig
Configuration for serialization of the .tim file.
comments : List[str]
Header comments from the .tim file.
timeseries : List[TimRecord]
A list of TimRecord objects, each containing a time value and associated data.
quantities_names : Optional[List[str]]
List of names for the quantities in the timeseries.
serializer_config (TimSerializerConfig):
Configuration for serialization of the .tim file.
comments (List[str]):
Header comments from the .tim file.
timeseries (List[TimRecord]):
A list of TimRecord objects, each containing a time value and associated data.
quantities_names (Optional[List[str]]):
List of names for the quantities in the timeseries.
Methods:
--------
_ext() -> str
Returns the file extension for .tim files.
_filename() -> str
Returns the default filename for .tim files.
_get_serializer() -> Callable
Returns the serializer callable for .tim files.
_get_parser() -> Callable
Returns the parser callable for .tim files.
_validate_timeseries_values(cls, v: List[TimRecord]) -> List[TimRecord]
Validates the timeseries data.
as_dataframe(columns: List[Any] = None) -> DataFrame
Returns the timeseries as a pandas DataFrame.
_validate_quantities_names(cls, v, values) -> List[str]
Validates the quantities_names equals to the values or each record.
_ext() -> str:
Returns the file extension for .tim files.
_filename() -> str:
Returns the default filename for .tim files.
_get_serializer() -> Callable:
Returns the serializer callable for .tim files.
_get_parser() -> Callable:
Returns the parser callable for .tim files.
_validate_timeseries_values(cls, v: List[TimRecord]) -> List[TimRecord]:
Validates the timeseries data.
as_dataframe(columns: List[Any] = None) -> DataFrame:
Returns the timeseries as a pandas DataFrame.
_validate_quantities_names(cls, v, values) -> List[str]:
Validates that quantities_names match the values or each record.
Args:
-----
filepath : Path
Path to the .tim file.
data : Dict
Parsed data containing comments and timeseries.
serializer_config : TimSerializerConfig
Configuration for serializing the .tim file.
filepath (Path):
Path to the .tim file.
data (Dict):
Parsed data containing comments and timeseries.
serializer_config (TimSerializerConfig):
Configuration for serializing the .tim file.
Returns:
--------
List[TimRecord]
Validated list of TimRecord objects.
List[TimRecord]:
Validated list of TimRecord objects.
Raises:
-------
ValueError
If the timeseries has inconsistent column counts or duplicate time values.
ValueError:
If the timeseries has inconsistent column counts or duplicate time values.
Examples:
---------
Create a TimModel object from a .tim file:
>>> from hydrolib.core.dflowfm.tim.models import TimModel, TimRecord
>>> tim_model = TimModel(filepath="tests/data/input/tim/triple_data_for_timeseries.tim")
>>> print(tim_model.timeseries)
[TimRecord(time=10.0, data=[1.232, 2.343, 3.454]), TimRecord(time=20.0, data=[4.565, 5.676, 6.787]), TimRecord(time=30.0, data=[1.5, 2.6, 3.7])]
Create `TimModel` from `TimRecord` objects:
>>> new_tim = TimModel()
>>> new_tim.comments = ["# Example comment"]
>>> new_tim.timeseries = [TimRecord(time=0.0, data=[1.0, 2.0])]
Serialize the `TimModel` to a .tim file:
>>> new_tim.save(filepath="output.tim") # doctest: +SKIP
Create a TimModel object from a .tim file:
>>> from hydrolib.core.dflowfm.tim.models import TimModel, TimRecord
>>> tim_model = TimModel(filepath="tests/data/input/tim/triple_data_for_timeseries.tim")
>>> print(tim_model.timeseries)
[TimRecord(time=10.0, data=[1.232, 2.343, 3.454]), TimRecord(time=20.0, data=[4.565, 5.676, 6.787]), TimRecord(time=30.0, data=[1.5, 2.6, 3.7])]
Provide names for the quantities in the timeseries:
>>> quantities_names = ["discharge", "waterlevel", "salinity", "temperature", "initialtracer"]
>>> tim_model = TimModel(filepath="tests/data/input/source-sink/tim-5-columns.tim", quantities_names=quantities_names)
>>> print(tim_model.quantities_names)
['discharge', 'waterlevel', 'salinity', 'temperature', 'initialtracer']
>>> print(tim_model.as_dataframe())
discharge waterlevel salinity temperature initialtracer
0.0 1.0 2.0 3.0 4.0 5.0
100.0 1.0 2.0 3.0 4.0 5.0
200.0 1.0 2.0 3.0 4.0 5.0
300.0 1.0 2.0 3.0 4.0 5.0
400.0 1.0 2.0 3.0 4.0 5.0
Create a `TimModel` object from a dictionary:
>>> data = {
... "comments": ["# Example comment"],
... "timeseries": [TimRecord(time=0.0, data=[1.0, 2.0])]
... }
>>> tim_model = TimModel(**data)
>>> print(tim_model.timeseries)
[TimRecord(time=0.0, data=[1.0, 2.0])]
Create `TimModel` from `TimRecord` objects:
>>> new_tim = TimModel()
>>> new_tim.comments = ["# Example comment"]
>>> new_tim.timeseries = [TimRecord(time=0.0, data=[1.0, 2.0])]
Serialize the `TimModel` to a .tim file:
>>> new_tim.save(filepath="output.tim") # doctest: +SKIP
See Also:
---------
TimParser
Used for parsing .tim files.
TimSerializer
Used for serializing .tim files.
TimRecord
Represents individual time and data entries in the timeseries.
TimParser: Used for parsing .tim files.
TimSerializer: Used for serializing .tim files.
TimRecord: Represents individual time and data entries in the timeseries.
Notes:
------
This class ensures the integrity of the timeseries by validating data consistency and detecting duplicate time entries.
This class ensures the integrity of the timeseries by validating data consistency and detecting duplicate time entries.
References:
- `TIM file format <https://content.oss.deltares.nl/delft3dfm1d2d/D-Flow_FM_User_Manual_1D2D.pdf#C4>`_
Expand Down Expand Up @@ -215,25 +227,41 @@ def as_dataframe(self, columns: List[Any] = None) -> DataFrame:
Returns:
DataFrame: The timeseries as a pandas DataFrame.
Notes:
- If the columns are not provided, the quantities_names will be used as column names.
- If the quantities_names are not provided, the columns will be named as 0, 1, 2, etc.
Examples:
---------
>>> from hydrolib.core.dflowfm.tim.models import TimModel
>>> tim_model = TimModel(filepath="tests/data/input/tim/triple_data_for_timeseries.tim")
>>> df = tim_model.as_dataframe()
>>> print(df)
0 1 2
10.0 1.232 2.343 3.454
20.0 4.565 5.676 6.787
30.0 1.500 2.600 3.700
To add column names to the DataFrame:
>>> df = tim_model.as_dataframe(columns=["Column1", "Column2", "Column3"])
>>> print(df)
Column1 Column2 Column3
10.0 1.232 2.343 3.454
20.0 4.565 5.676 6.787
30.0 1.500 2.600 3.700
Create a `TimModel` object from a .tim file:
>>> from hydrolib.core.dflowfm.tim.models import TimModel
>>> tim_model = TimModel(filepath="tests/data/input/tim/triple_data_for_timeseries.tim")
>>> df = tim_model.as_dataframe()
>>> print(df)
0 1 2
10.0 1.232 2.343 3.454
20.0 4.565 5.676 6.787
30.0 1.500 2.600 3.700
If the `TimModel` object was created with quantities names:
>>> quantities_names = ["Column1", "Column2", "Column3"]
>>> tim_model = TimModel(filepath="tests/data/input/tim/triple_data_for_timeseries.tim", quantities_names=quantities_names)
>>> df = tim_model.as_dataframe()
>>> print(df)
Column1 Column2 Column3
10.0 1.232 2.343 3.454
20.0 4.565 5.676 6.787
30.0 1.500 2.600 3.700
To add column names to the DataFrame after you have created the `TimModel` object:
>>> df = tim_model.as_dataframe(columns=["Column1", "Column2", "Column3"])
>>> print(df)
Column1 Column2 Column3
10.0 1.232 2.343 3.454
20.0 4.565 5.676 6.787
30.0 1.500 2.600 3.700
"""
time_series = [record.data for record in self.timeseries]
index = [record.time for record in self.timeseries]
if not columns:
columns = self.quantities_names
return DataFrame(time_series, index=index, columns=columns)
5 changes: 5 additions & 0 deletions tests/data/input/source-sink/tim-5-columns.tim
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
0.0 1.0 2.0 3.0 4.0 5.0
100 1.0 2.0 3.0 4.0 5.0
200 1.0 2.0 3.0 4.0 5.0
300 1.0 2.0 3.0 4.0 5.0
400 1.0 2.0 3.0 4.0 5.0
6 changes: 6 additions & 0 deletions tests/dflowfm/test_tim.py
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,12 @@ def test_initialization(self):
assert model.as_dataframe().empty

def test_initialize_with_quantities_names(self, input_files_dir: Path):
"""
Test Initializing the `TimModel` from a file and provide the name of the quantities in the files.
The initialization should initizline the super class `BaseModel` with the file path.
The `quantities_names` is used to initialize the `quantities_names` attribute.
"""
path = input_files_dir / "tim/single_data_for_timeseries.tim"
model = TimModel(path, quantities_names=["a"])
assert model.quantities_names == ["a"]
Expand Down

0 comments on commit aef2375

Please sign in to comment.