Skip to content

TimeSeries

Bases: TaggedTable

Source code in src/safeds/data/tabular/containers/_time_series.py
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
class TimeSeries(TaggedTable):

    # ------------------------------------------------------------------------------------------------------------------
    # Creation
    # ------------------------------------------------------------------------------------------------------------------
    @staticmethod
    def _from_tagged_table(
        tagged_table: TaggedTable,
        time_name: str,
    ) -> TimeSeries:
        """Create a time series from a tagged table.

        Parameters
        ----------
        table : TaggedTable
            The tagged table.
        time_name: str
            Name of the time column.

        Returns
        -------
        time_series : TimeSeries
            the created time series

        Raises
        ------
        UnknownColumnNameError
            If time_name matches none of the column names.
        Value Error
            If time column is also a feature column

        Examples
        --------
        >>> from safeds.data.tabular.containers import Table, TimeSeries
        >>> tagged_table = TaggedTable({"date": ["01.01", "01.02", "01.03", "01.04"], "col1": ["a", "b", "c", "a"]}, "col1" )
        >>> timeseries = TimeSeries._from_tagged_table(tagged_table, time_name = "date")
        """
        if time_name not in tagged_table.column_names:
            raise UnknownColumnNameError([time_name])
        table = tagged_table._as_table()
        # make sure that the time_name is not part of the features
        result = object.__new__(TimeSeries)
        feature_names = tagged_table.features.column_names
        if time_name in feature_names:
            feature_names.remove(time_name)

        if time_name == tagged_table.target.name:
            raise ValueError(f"Column '{time_name}' cannot be both time column and target.")

        result._data = table._data
        result._schema = table.schema
        result._time = table.get_column(time_name)
        result._features = table.keep_only_columns(feature_names)
        result._target = table.get_column(tagged_table.target.name)
        return result

    @staticmethod
    def _from_table_to_time_series(
        table: Table,
        target_name: str,
        time_name: str,
        feature_names: list[str] | None = None,
    ) -> TimeSeries:
        """Create a TimeSeries from a table.

        Parameters
        ----------
        table : Table
            The table.
        target_name : str
            Name of the target column.
        time_name: str
            Name of the date column.
        feature_names : list[str] | None
            Names of the feature columns. If None, all columns except the target and time columns are used.

        Returns
        -------
        time_series : TimeSeries
            the created time series

        Raises
        ------
        UnknownColumnNameError
            If target_name or time_name matches none of the column names.
        Value Error
            If there is no other column than the specified target and time columns left to be a feature column
        Value Error
            If one column is target and feature
        Value Error
            If one column is time and feature

        Examples
        --------
        >>> from safeds.data.tabular.containers import Table, TimeSeries
        >>> table = Table({"date": ["01.01", "01.02", "01.03", "01.04"], "f1": ["a", "b", "c", "a"], "t": [1,2,3,4]})
        >>> timeseries = TimeSeries._from_table_to_time_series(table, "t", "date", ["f1"])
        """
        if feature_names is not None and time_name in feature_names:
            raise ValueError(f"Column '{time_name}' can not be time and feature column.")

        if feature_names is None:
            feature_names = table.column_names
            if time_name in feature_names:
                feature_names.remove(time_name)
            if target_name in feature_names:
                feature_names.remove(target_name)
        tagged_table = TaggedTable._from_table(table=table, target_name=target_name, feature_names=feature_names)
        # check if time column got added as feature column
        return TimeSeries._from_tagged_table(tagged_table=tagged_table, time_name=time_name)

    # ------------------------------------------------------------------------------------------------------------------
    # Dunder methods
    # ------------------------------------------------------------------------------------------------------------------

    def __init__(
        self,
        data: Mapping[str, Sequence[Any]],
        target_name: str,
        time_name: str,
        feature_names: list[str] | None = None,
    ):
        """
        Create a time series from a mapping of column names to their values.

        Parameters
        ----------
        data : Mapping[str, Sequence[Any]]
            The data.
        target_name : str
            Name of the target column.
        time_name : str
            Name of the time column
        feature_names : list[str] | None
            Names of the feature columns. If None, all columns except the target and time columns are used.

        Raises
        ------
        ColumnLengthMismatchError
            If columns have different lengths.
        ValueError
            If the target column is also a feature column.
        ValueError
            If no feature columns are specified.
        ValueError
            If time column is also a feature column
        UnknownColumnNameError
            If time column does not exist

        Examples
        --------
        >>> from safeds.data.tabular.containers import TaggedTable
        >>> table = TaggedTable({"a": [1, 2, 3], "b": [4, 5, 6]}, "b", ["a"])
        """
        _data = Table(data)

        if feature_names is None:
            feature_names = _data.column_names
            if time_name in feature_names:
                feature_names.remove(time_name)
            if target_name in feature_names:
                feature_names.remove(target_name)

        # Validate inputs
        super().__init__(data, target_name, feature_names)
        if time_name in feature_names:
            raise ValueError(f"Column '{time_name}' can not be time and feature column.")
        if time_name not in (_data.column_names):
            raise UnknownColumnNameError([time_name])
        self._time: Column = _data.get_column(time_name)

    def __sizeof__(self) -> int:
        """
        Return the complete size of this object.

        Returns
        -------
        Size of this object in bytes.
        """
        return TaggedTable.__sizeof__(self) + sys.getsizeof(self._time)

    # ------------------------------------------------------------------------------------------------------------------
    # Properties
    # ------------------------------------------------------------------------------------------------------------------

    @property
    def time(self) -> Column:
        """
        Get the time column of the time series.

        Returns
        -------
        Column
            The time column.
        """
        return self._time

    # ------------------------------------------------------------------------------------------------------------------
    # Overriden methods from TaggedTable class:
    # ------------------------------------------------------------------------------------------------------------------
    def _as_table(self: TimeSeries) -> Table:
        """
        Return a new `Table` with the tagging removed.

        The original time series is not modified.

        Parameters
        ----------
        self: TimeSeries
            The Time Series.

        Returns
        -------
        table: Table
            The time series as an untagged Table, i.e. without the information about which columns are features, target or time.

        """
        return Table.from_columns(super().to_columns())

    def add_column(self, column: Column) -> TimeSeries:
        """
        Return a new `TimeSeries` with the provided column attached at the end, as neither target nor feature column.

        The original time series is not modified.

        Parameters
        ----------
        column : Column
            The column to be added.

        Returns
        -------
        result : TimeSeries
            The time series with the column attached as neither target nor feature column.

        Raises
        ------
        DuplicateColumnNameError
            If the new column already exists.
        ColumnSizeError
            If the size of the column does not match the number of rows.
        """
        return TimeSeries._from_tagged_table(
            super().add_column(column),
            time_name=self.time.name,
        )

    def add_column_as_feature(self, column: Column) -> TimeSeries:
        """
        Return a new `TimeSeries` with the provided column attached at the end, as a feature column.

        the original time series is not modified.

        Parameters
        ----------
        column : Column
            The column to be added.

        Returns
        -------
        result : TimeSeries
            The time series with the attached feature column.

        Raises
        ------
        DuplicateColumnNameError
            If the new column already exists.
        ColumnSizeError
            If the size of the column does not match the number of rows.
        """
        return TimeSeries._from_tagged_table(
            super().add_column_as_feature(column),
            time_name=self.time.name,
        )

    def add_columns_as_features(self, columns: list[Column] | Table) -> TimeSeries:
        """
        Return a new `TimeSeries` with the provided columns attached at the end, as feature columns.

        The original time series is not modified.

        Parameters
        ----------
        columns : list[Column] | Table
            The columns to be added as features.

        Returns
        -------
        result : TimeSeries
            The time series with the attached feature columns.

        Raises
        ------
        DuplicateColumnNameError
            If any of the new feature columns already exist.
        ColumnSizeError
            If the size of any feature column does not match the number of rows.
        """
        return TimeSeries._from_tagged_table(
            super().add_columns_as_features(columns),
            time_name=self.time.name,
        )

    def add_columns(self, columns: list[Column] | Table) -> TimeSeries:
        """
        Return a new `TimeSeries` with multiple added columns, as neither target nor feature columns.

        The original time series is not modified.

        Parameters
        ----------
        columns : list[Column] or Table
            The columns to be added.

        Returns
        -------
        result: TimeSeries
            A new time series combining the original table and the given columns as neither target nor feature columns.

        Raises
        ------
        DuplicateColumnNameError
            If at least one column name from the provided column list already exists in the time series.
        ColumnSizeError
            If at least one of the column sizes from the provided column list does not match the time series.
        """
        return TimeSeries._from_tagged_table(
            super().add_columns(columns),
            time_name=self.time.name,
        )

    def add_row(self, row: Row) -> TimeSeries:
        """
        Return a new `TimeSeries` with an extra Row attached.

        The original time series is not modified.

        Parameters
        ----------
        row : Row
            The row to be added.

        Returns
        -------
        table : TimeSeries
            A new time series with the added row at the end.

        Raises
        ------
        UnknownColumnNameError
            If the row has different column names than the time series.
        """
        return TimeSeries._from_tagged_table(super().add_row(row), time_name=self.time.name)

    def add_rows(self, rows: list[Row] | Table) -> TimeSeries:
        """
        Return a new `TimeSeries` with multiple extra Rows attached.

        The original time series is not modified.

        Parameters
        ----------
        rows : list[Row] or Table
            The rows to be added.

        Returns
        -------
        result : TimeSeries
            A new time series which combines the original time series and the given rows.

        Raises
        ------
        UnknownColumnNameError
            If at least one of the rows have different column names than the time series.
        """
        return TimeSeries._from_tagged_table(super().add_rows(rows), time_name=self.time.name)

    def filter_rows(self, query: Callable[[Row], bool]) -> TimeSeries:
        """
        Return a new `TimeSeries` containing only rows that match the given Callable (e.g. lambda function).

        The original time series is not modified.

        Parameters
        ----------
        query : lambda function
            A Callable that is applied to all rows.

        Returns
        -------
        result: TimeSeries
            A time series containing only the rows to match the query.
        """
        return TimeSeries._from_tagged_table(
            super().filter_rows(query),
            time_name=self.time.name,
        )

    def keep_only_columns(self, column_names: list[str]) -> TimeSeries:
        """
        Return a new `TimeSeries` with only the given column(s).

        The original time series is not modified.

        Parameters
        ----------
        column_names : list[str]
            A list containing the columns to be kept.

        Returns
        -------
        table : TimeSeries
            A time series containing only the given column(s).

        Raises
        ------
        UnknownColumnNameError
            If any of the given columns does not exist.
        IllegalSchemaModificationError
            If none of the given columns is the target or time column or any of the feature columns.
        """
        if self.target.name not in column_names:
            raise IllegalSchemaModificationError("Must keep the target column.")
        if len(set(self.features.column_names).intersection(set(column_names))) == 0:
            raise IllegalSchemaModificationError("Must keep at least one feature column.")
        if self.time.name not in column_names:
            raise IllegalSchemaModificationError("Must keep the time column.")
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                super().keep_only_columns(column_names),
                target_name=self.target.name,
                feature_names=sorted(
                    set(self.features.column_names).intersection(set(column_names)),
                    key={val: ix for ix, val in enumerate(self.features.column_names)}.__getitem__,
                ),
            ),
            time_name=self.time.name,
        )

    def remove_columns(self, column_names: list[str]) -> TimeSeries:
        """
        Return a new `TimeSeries` with the given column(s) removed from the time series.

        The original time series is not modified.

        Parameters
        ----------
        column_names : list[str]
            The names of all columns to be dropped.

        Returns
        -------
        table : TimeSeries
            A time series without the given columns.

        Raises
        ------
        UnknownColumnNameError
            If any of the given columns does not exist.
        ColumnIsTargetError
            If any of the given columns is the target column.
        ColumnIsTimeError
            If any of the given columns is the time column.
        IllegalSchemaModificationError
            If the given columns contain all the feature columns.
        """
        if self.target.name in column_names:
            raise ColumnIsTargetError(self.target.name)
        if len(set(self.features.column_names) - set(column_names)) == 0:
            raise IllegalSchemaModificationError("You cannot remove every feature column.")
        if self.time.name in column_names:
            raise ColumnIsTimeError(self.time.name)
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                super().remove_columns(column_names),
                target_name=self.target.name,
                feature_names=sorted(
                    set(self.features.column_names) - set(column_names),
                    key={val: ix for ix, val in enumerate(self.features.column_names)}.__getitem__,
                ),
            ),
            time_name=self.time.name,
        )

    def remove_columns_with_missing_values(self) -> TimeSeries:
        """
        Return a new `TimeSeries` with every column that misses values removed.

        The original time series is not modified.

        Returns
        -------
        table : TimeSeries
            A time series without the columns that contain missing values.

        Raises
        ------
        ColumnIsTargetError
            If any of the columns to be removed is the target column.
        ColumnIsTimeError
            If any of the columns to be removed is the time column.
        IllegalSchemaModificationError
            If the columns to remove contain all the feature columns.
        """
        table = super().remove_columns_with_missing_values()
        if self.time.name not in table.column_names:
            raise ColumnIsTimeError(self.time.name)
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                table,
                self.target.name,
                feature_names=sorted(
                    set(self.features.column_names).intersection(set(table.column_names)),
                    key={val: ix for ix, val in enumerate(self.features.column_names)}.__getitem__,
                ),
            ),
            time_name=self.time.name,
        )

    def remove_columns_with_non_numerical_values(self) -> TimeSeries:
        """
        Return a new `TimeSeries` with every column that contains non-numerical values removed.

        The original time series is not modified.

        Returns
        -------
        table : TimeSeries
            A time series without the columns that contain non-numerical values.

        Raises
        ------
        ColumnIsTargetError
            If any of the columns to be removed is the target column.
        ColumnIsTimeError
            If any of the columns to be removed is the time column.
        IllegalSchemaModificationError
            If the columns to remove contain all the feature columns.
        """
        table = super().remove_columns_with_non_numerical_values()
        if self.time.name not in table.column_names:
            raise ColumnIsTimeError(self.time.name)
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                table,
                self.target.name,
                feature_names=sorted(
                    set(self.features.column_names).intersection(set(table.column_names)),
                    key={val: ix for ix, val in enumerate(self.features.column_names)}.__getitem__,
                ),
            ),
            time_name=self.time.name,
        )

    def remove_duplicate_rows(self) -> TimeSeries:
        """
        Return a new `TimeSeries` with all row duplicates removed.

        The original time series is not modified.

        Returns
        -------
        result : TimeSeries
            The time series with the duplicate rows removed.
        """
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                super().remove_duplicate_rows(),
                target_name=self.target.name,
                feature_names=self.features.column_names,
            ),
            time_name=self.time.name,
        )

    def remove_rows_with_missing_values(self) -> TimeSeries:
        """
        Return a new `TimeSeries` without the rows that contain missing values.

        The original time series is not modified.

        Returns
        -------
        table : TimeSeries
            A time series without the rows that contain missing values.
        """
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                super().remove_rows_with_missing_values(),
                target_name=self.target.name,
                feature_names=self.features.column_names,
            ),
            time_name=self.time.name,
        )

    def remove_rows_with_outliers(self) -> TimeSeries:
        """
        Return a new `TimeSeries` with all rows that contain at least one outlier removed.

        We define an outlier as a value that has a distance of more than 3 standard deviations from the column mean.
        Missing values are not considered outliers. They are also ignored during the calculation of the standard
        deviation.

        The original time series is not modified.

        Returns
        -------
        new_time_series : TimeSeries
            A new time series without rows containing outliers.
        """
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                super().remove_rows_with_outliers(),
                target_name=self.target.name,
                feature_names=self.features.column_names,
            ),
            time_name=self.time.name,
        )

    def rename_column(self, old_name: str, new_name: str) -> TimeSeries:
        """
        Return a new `TimeSeries` with a single column renamed.

        The original time series is not modified.

        Parameters
        ----------
        old_name : str
            The old name of the column.
        new_name : str
            The new name of the column.

        Returns
        -------
        table : TimeSeries
            The time series with the renamed column.

        Raises
        ------
        UnknownColumnNameError
            If the specified old target column name does not exist.
        DuplicateColumnNameError
            If the specified new target column name already exists.
        """
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                super().rename_column(old_name, new_name),
                target_name=new_name if self.target.name == old_name else self.target.name,
                feature_names=(
                    self.features.column_names
                    if old_name not in self.features.column_names
                    else [
                        column_name if column_name != old_name else new_name
                        for column_name in self.features.column_names
                    ]
                ),
            ),
            time_name=new_name if self.time.name == old_name else self.time.name,
        )

    def replace_column(self, old_column_name: str, new_columns: list[Column]) -> TimeSeries:
        """
        Return a new `TimeSeries` with the specified old column replaced by a list of new columns.

        If the column to be replaced is the target or time column, it must be replaced by exactly one column. That column
        becomes the new target or time column. If the column to be replaced is a feature column, the new columns that replace it
        all become feature columns.

        The order of columns is kept. The original time series is not modified.

        Parameters
        ----------
        old_column_name : str
            The name of the column to be replaced.
        new_columns : list[Column]
            The new columns replacing the old column.

        Returns
        -------
        result : TimeSeries
            A time series with the old column replaced by the new columns.

        Raises
        ------
        UnknownColumnNameError
            If the old column does not exist.
        DuplicateColumnNameError
            If the new column already exists and the existing column is not affected by the replacement.
        ColumnSizeError
            If the size of the column does not match the amount of rows.
        IllegalSchemaModificationError
            If the target or time column would be removed or replaced by more than one column.
        """
        if old_column_name == self.time.name:
            if len(new_columns) != 1:
                raise IllegalSchemaModificationError(
                    f'Time column "{self.time.name}" can only be replaced by exactly one new column.',
                )
            else:
                return TimeSeries._from_tagged_table(
                    TaggedTable._from_table(
                        super().replace_column(old_column_name, new_columns),
                        target_name=self.target.name,
                        feature_names=self.features.column_names,
                    ),
                    time_name=new_columns[0].name,
                )
        if old_column_name == self.target.name:
            if len(new_columns) != 1:
                raise IllegalSchemaModificationError(
                    f'Target column "{self.target.name}" can only be replaced by exactly one new column.',
                )
            else:
                return TimeSeries._from_tagged_table(
                    TaggedTable._from_table(
                        super().replace_column(old_column_name, new_columns),
                        target_name=new_columns[0].name,
                        feature_names=self.features.column_names,
                    ),
                    time_name=self.time.name,
                )
        else:
            return TimeSeries._from_tagged_table(
                TaggedTable._from_table(
                    super().replace_column(old_column_name, new_columns),
                    target_name=self.target.name,
                    feature_names=(
                        self.features.column_names
                        if old_column_name not in self.features.column_names
                        else self.features.column_names[: self.features.column_names.index(old_column_name)]
                        + [col.name for col in new_columns]
                        + self.features.column_names[self.features.column_names.index(old_column_name) + 1 :]
                    ),
                ),
                time_name=self.time.name,
            )

    def slice_rows(
        self,
        start: int | None = None,
        end: int | None = None,
        step: int = 1,
    ) -> TimeSeries:
        """
        Slice a part of the table into a new `TimeSeries`.

        The original time series is not modified.

        Parameters
        ----------
        start : int | None
            The first index of the range to be copied into a new time series, None by default.
        end : int | None
            The last index of the range to be copied into a new time series, None by default.
        step : int
            The step size used to iterate through the time series, 1 by default.

        Returns
        -------
        result : TimeSeries
            The resulting time series.

        Raises
        ------
        IndexOutOfBoundsError
            If the index is out of bounds.
        """
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                super().slice_rows(start, end, step),
                target_name=self.target.name,
                feature_names=self.features.column_names,
            ),
            time_name=self.time.name,
        )

    def sort_columns(
        self,
        comparator: Callable[[Column, Column], int] = lambda col1, col2: (col1.name > col2.name)
        - (col1.name < col2.name),
    ) -> TimeSeries:
        """
        Sort the columns of a `TimeSeries` with the given comparator and return a new `TimeSeries`.

        The comparator is a function that takes two columns `col1` and `col2` and
        returns an integer:

        * If the function returns a negative number, `col1` will be ordered before `col2`.
        * If the function returns a positive number, `col1` will be ordered after `col2`.
        * If the function returns 0, the original order of `col1` and `col2` will be kept.

        If no comparator is given, the columns will be sorted alphabetically by their name.

        The original time series is not modified.

        Parameters
        ----------
        comparator : Callable[[Column, Column], int]
            The function used to compare two columns.

        Returns
        -------
        new_time_series : TimeSeries
            A new time series with sorted columns.
        """
        sorted_table = super().sort_columns(comparator)
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                sorted_table,
                target_name=self.target.name,
                feature_names=sorted(
                    set(sorted_table.column_names).intersection(self.features.column_names),
                    key={val: ix for ix, val in enumerate(sorted_table.column_names)}.__getitem__,
                ),
            ),
            time_name=self.time.name,
        )

    def transform_column(self, name: str, transformer: Callable[[Row], Any]) -> TimeSeries:
        """
        Return a new `TimeSeries` with the provided column transformed by calling the provided transformer.

        The original time series is not modified.

        Returns
        -------
        result : TimeSeries
            The time series with the transformed column.

        Raises
        ------
        UnknownColumnNameError
            If the column does not exist.
        """
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                super().transform_column(name, transformer),
                target_name=self.target.name,
                feature_names=self.features.column_names,
            ),
            time_name=self.time.name,
        )

time: Column property

Get the time column of the time series.

Returns:

Type Description
Column

The time column.

__init__(data, target_name, time_name, feature_names=None)

Create a time series from a mapping of column names to their values.

Parameters:

Name Type Description Default
data Mapping[str, Sequence[Any]]

The data.

required
target_name str

Name of the target column.

required
time_name str

Name of the time column

required
feature_names list[str] | None

Names of the feature columns. If None, all columns except the target and time columns are used.

None

Raises:

Type Description
ColumnLengthMismatchError

If columns have different lengths.

ValueError

If the target column is also a feature column.

ValueError

If no feature columns are specified.

ValueError

If time column is also a feature column

UnknownColumnNameError

If time column does not exist

Examples:

>>> from safeds.data.tabular.containers import TaggedTable
>>> table = TaggedTable({"a": [1, 2, 3], "b": [4, 5, 6]}, "b", ["a"])
Source code in src/safeds/data/tabular/containers/_time_series.py
def __init__(
    self,
    data: Mapping[str, Sequence[Any]],
    target_name: str,
    time_name: str,
    feature_names: list[str] | None = None,
):
    """
    Create a time series from a mapping of column names to their values.

    Parameters
    ----------
    data : Mapping[str, Sequence[Any]]
        The data.
    target_name : str
        Name of the target column.
    time_name : str
        Name of the time column
    feature_names : list[str] | None
        Names of the feature columns. If None, all columns except the target and time columns are used.

    Raises
    ------
    ColumnLengthMismatchError
        If columns have different lengths.
    ValueError
        If the target column is also a feature column.
    ValueError
        If no feature columns are specified.
    ValueError
        If time column is also a feature column
    UnknownColumnNameError
        If time column does not exist

    Examples
    --------
    >>> from safeds.data.tabular.containers import TaggedTable
    >>> table = TaggedTable({"a": [1, 2, 3], "b": [4, 5, 6]}, "b", ["a"])
    """
    _data = Table(data)

    if feature_names is None:
        feature_names = _data.column_names
        if time_name in feature_names:
            feature_names.remove(time_name)
        if target_name in feature_names:
            feature_names.remove(target_name)

    # Validate inputs
    super().__init__(data, target_name, feature_names)
    if time_name in feature_names:
        raise ValueError(f"Column '{time_name}' can not be time and feature column.")
    if time_name not in (_data.column_names):
        raise UnknownColumnNameError([time_name])
    self._time: Column = _data.get_column(time_name)

__sizeof__()

Return the complete size of this object.

Returns:

Type Description
Size of this object in bytes.
Source code in src/safeds/data/tabular/containers/_time_series.py
def __sizeof__(self) -> int:
    """
    Return the complete size of this object.

    Returns
    -------
    Size of this object in bytes.
    """
    return TaggedTable.__sizeof__(self) + sys.getsizeof(self._time)

add_column(column)

Return a new TimeSeries with the provided column attached at the end, as neither target nor feature column.

The original time series is not modified.

Parameters:

Name Type Description Default
column Column

The column to be added.

required

Returns:

Name Type Description
result TimeSeries

The time series with the column attached as neither target nor feature column.

Raises:

Type Description
DuplicateColumnNameError

If the new column already exists.

ColumnSizeError

If the size of the column does not match the number of rows.

Source code in src/safeds/data/tabular/containers/_time_series.py
def add_column(self, column: Column) -> TimeSeries:
    """
    Return a new `TimeSeries` with the provided column attached at the end, as neither target nor feature column.

    The original time series is not modified.

    Parameters
    ----------
    column : Column
        The column to be added.

    Returns
    -------
    result : TimeSeries
        The time series with the column attached as neither target nor feature column.

    Raises
    ------
    DuplicateColumnNameError
        If the new column already exists.
    ColumnSizeError
        If the size of the column does not match the number of rows.
    """
    return TimeSeries._from_tagged_table(
        super().add_column(column),
        time_name=self.time.name,
    )

add_column_as_feature(column)

Return a new TimeSeries with the provided column attached at the end, as a feature column.

the original time series is not modified.

Parameters:

Name Type Description Default
column Column

The column to be added.

required

Returns:

Name Type Description
result TimeSeries

The time series with the attached feature column.

Raises:

Type Description
DuplicateColumnNameError

If the new column already exists.

ColumnSizeError

If the size of the column does not match the number of rows.

Source code in src/safeds/data/tabular/containers/_time_series.py
def add_column_as_feature(self, column: Column) -> TimeSeries:
    """
    Return a new `TimeSeries` with the provided column attached at the end, as a feature column.

    the original time series is not modified.

    Parameters
    ----------
    column : Column
        The column to be added.

    Returns
    -------
    result : TimeSeries
        The time series with the attached feature column.

    Raises
    ------
    DuplicateColumnNameError
        If the new column already exists.
    ColumnSizeError
        If the size of the column does not match the number of rows.
    """
    return TimeSeries._from_tagged_table(
        super().add_column_as_feature(column),
        time_name=self.time.name,
    )

add_columns(columns)

Return a new TimeSeries with multiple added columns, as neither target nor feature columns.

The original time series is not modified.

Parameters:

Name Type Description Default
columns list[Column] or Table

The columns to be added.

required

Returns:

Name Type Description
result TimeSeries

A new time series combining the original table and the given columns as neither target nor feature columns.

Raises:

Type Description
DuplicateColumnNameError

If at least one column name from the provided column list already exists in the time series.

ColumnSizeError

If at least one of the column sizes from the provided column list does not match the time series.

Source code in src/safeds/data/tabular/containers/_time_series.py
def add_columns(self, columns: list[Column] | Table) -> TimeSeries:
    """
    Return a new `TimeSeries` with multiple added columns, as neither target nor feature columns.

    The original time series is not modified.

    Parameters
    ----------
    columns : list[Column] or Table
        The columns to be added.

    Returns
    -------
    result: TimeSeries
        A new time series combining the original table and the given columns as neither target nor feature columns.

    Raises
    ------
    DuplicateColumnNameError
        If at least one column name from the provided column list already exists in the time series.
    ColumnSizeError
        If at least one of the column sizes from the provided column list does not match the time series.
    """
    return TimeSeries._from_tagged_table(
        super().add_columns(columns),
        time_name=self.time.name,
    )

add_columns_as_features(columns)

Return a new TimeSeries with the provided columns attached at the end, as feature columns.

The original time series is not modified.

Parameters:

Name Type Description Default
columns list[Column] | Table

The columns to be added as features.

required

Returns:

Name Type Description
result TimeSeries

The time series with the attached feature columns.

Raises:

Type Description
DuplicateColumnNameError

If any of the new feature columns already exist.

ColumnSizeError

If the size of any feature column does not match the number of rows.

Source code in src/safeds/data/tabular/containers/_time_series.py
def add_columns_as_features(self, columns: list[Column] | Table) -> TimeSeries:
    """
    Return a new `TimeSeries` with the provided columns attached at the end, as feature columns.

    The original time series is not modified.

    Parameters
    ----------
    columns : list[Column] | Table
        The columns to be added as features.

    Returns
    -------
    result : TimeSeries
        The time series with the attached feature columns.

    Raises
    ------
    DuplicateColumnNameError
        If any of the new feature columns already exist.
    ColumnSizeError
        If the size of any feature column does not match the number of rows.
    """
    return TimeSeries._from_tagged_table(
        super().add_columns_as_features(columns),
        time_name=self.time.name,
    )

add_row(row)

Return a new TimeSeries with an extra Row attached.

The original time series is not modified.

Parameters:

Name Type Description Default
row Row

The row to be added.

required

Returns:

Name Type Description
table TimeSeries

A new time series with the added row at the end.

Raises:

Type Description
UnknownColumnNameError

If the row has different column names than the time series.

Source code in src/safeds/data/tabular/containers/_time_series.py
def add_row(self, row: Row) -> TimeSeries:
    """
    Return a new `TimeSeries` with an extra Row attached.

    The original time series is not modified.

    Parameters
    ----------
    row : Row
        The row to be added.

    Returns
    -------
    table : TimeSeries
        A new time series with the added row at the end.

    Raises
    ------
    UnknownColumnNameError
        If the row has different column names than the time series.
    """
    return TimeSeries._from_tagged_table(super().add_row(row), time_name=self.time.name)

add_rows(rows)

Return a new TimeSeries with multiple extra Rows attached.

The original time series is not modified.

Parameters:

Name Type Description Default
rows list[Row] or Table

The rows to be added.

required

Returns:

Name Type Description
result TimeSeries

A new time series which combines the original time series and the given rows.

Raises:

Type Description
UnknownColumnNameError

If at least one of the rows have different column names than the time series.

Source code in src/safeds/data/tabular/containers/_time_series.py
def add_rows(self, rows: list[Row] | Table) -> TimeSeries:
    """
    Return a new `TimeSeries` with multiple extra Rows attached.

    The original time series is not modified.

    Parameters
    ----------
    rows : list[Row] or Table
        The rows to be added.

    Returns
    -------
    result : TimeSeries
        A new time series which combines the original time series and the given rows.

    Raises
    ------
    UnknownColumnNameError
        If at least one of the rows have different column names than the time series.
    """
    return TimeSeries._from_tagged_table(super().add_rows(rows), time_name=self.time.name)

filter_rows(query)

Return a new TimeSeries containing only rows that match the given Callable (e.g. lambda function).

The original time series is not modified.

Parameters:

Name Type Description Default
query lambda function

A Callable that is applied to all rows.

required

Returns:

Name Type Description
result TimeSeries

A time series containing only the rows to match the query.

Source code in src/safeds/data/tabular/containers/_time_series.py
def filter_rows(self, query: Callable[[Row], bool]) -> TimeSeries:
    """
    Return a new `TimeSeries` containing only rows that match the given Callable (e.g. lambda function).

    The original time series is not modified.

    Parameters
    ----------
    query : lambda function
        A Callable that is applied to all rows.

    Returns
    -------
    result: TimeSeries
        A time series containing only the rows to match the query.
    """
    return TimeSeries._from_tagged_table(
        super().filter_rows(query),
        time_name=self.time.name,
    )

keep_only_columns(column_names)

Return a new TimeSeries with only the given column(s).

The original time series is not modified.

Parameters:

Name Type Description Default
column_names list[str]

A list containing the columns to be kept.

required

Returns:

Name Type Description
table TimeSeries

A time series containing only the given column(s).

Raises:

Type Description
UnknownColumnNameError

If any of the given columns does not exist.

IllegalSchemaModificationError

If none of the given columns is the target or time column or any of the feature columns.

Source code in src/safeds/data/tabular/containers/_time_series.py
def keep_only_columns(self, column_names: list[str]) -> TimeSeries:
    """
    Return a new `TimeSeries` with only the given column(s).

    The original time series is not modified.

    Parameters
    ----------
    column_names : list[str]
        A list containing the columns to be kept.

    Returns
    -------
    table : TimeSeries
        A time series containing only the given column(s).

    Raises
    ------
    UnknownColumnNameError
        If any of the given columns does not exist.
    IllegalSchemaModificationError
        If none of the given columns is the target or time column or any of the feature columns.
    """
    if self.target.name not in column_names:
        raise IllegalSchemaModificationError("Must keep the target column.")
    if len(set(self.features.column_names).intersection(set(column_names))) == 0:
        raise IllegalSchemaModificationError("Must keep at least one feature column.")
    if self.time.name not in column_names:
        raise IllegalSchemaModificationError("Must keep the time column.")
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            super().keep_only_columns(column_names),
            target_name=self.target.name,
            feature_names=sorted(
                set(self.features.column_names).intersection(set(column_names)),
                key={val: ix for ix, val in enumerate(self.features.column_names)}.__getitem__,
            ),
        ),
        time_name=self.time.name,
    )

remove_columns(column_names)

Return a new TimeSeries with the given column(s) removed from the time series.

The original time series is not modified.

Parameters:

Name Type Description Default
column_names list[str]

The names of all columns to be dropped.

required

Returns:

Name Type Description
table TimeSeries

A time series without the given columns.

Raises:

Type Description
UnknownColumnNameError

If any of the given columns does not exist.

ColumnIsTargetError

If any of the given columns is the target column.

ColumnIsTimeError

If any of the given columns is the time column.

IllegalSchemaModificationError

If the given columns contain all the feature columns.

Source code in src/safeds/data/tabular/containers/_time_series.py
def remove_columns(self, column_names: list[str]) -> TimeSeries:
    """
    Return a new `TimeSeries` with the given column(s) removed from the time series.

    The original time series is not modified.

    Parameters
    ----------
    column_names : list[str]
        The names of all columns to be dropped.

    Returns
    -------
    table : TimeSeries
        A time series without the given columns.

    Raises
    ------
    UnknownColumnNameError
        If any of the given columns does not exist.
    ColumnIsTargetError
        If any of the given columns is the target column.
    ColumnIsTimeError
        If any of the given columns is the time column.
    IllegalSchemaModificationError
        If the given columns contain all the feature columns.
    """
    if self.target.name in column_names:
        raise ColumnIsTargetError(self.target.name)
    if len(set(self.features.column_names) - set(column_names)) == 0:
        raise IllegalSchemaModificationError("You cannot remove every feature column.")
    if self.time.name in column_names:
        raise ColumnIsTimeError(self.time.name)
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            super().remove_columns(column_names),
            target_name=self.target.name,
            feature_names=sorted(
                set(self.features.column_names) - set(column_names),
                key={val: ix for ix, val in enumerate(self.features.column_names)}.__getitem__,
            ),
        ),
        time_name=self.time.name,
    )

remove_columns_with_missing_values()

Return a new TimeSeries with every column that misses values removed.

The original time series is not modified.

Returns:

Name Type Description
table TimeSeries

A time series without the columns that contain missing values.

Raises:

Type Description
ColumnIsTargetError

If any of the columns to be removed is the target column.

ColumnIsTimeError

If any of the columns to be removed is the time column.

IllegalSchemaModificationError

If the columns to remove contain all the feature columns.

Source code in src/safeds/data/tabular/containers/_time_series.py
def remove_columns_with_missing_values(self) -> TimeSeries:
    """
    Return a new `TimeSeries` with every column that misses values removed.

    The original time series is not modified.

    Returns
    -------
    table : TimeSeries
        A time series without the columns that contain missing values.

    Raises
    ------
    ColumnIsTargetError
        If any of the columns to be removed is the target column.
    ColumnIsTimeError
        If any of the columns to be removed is the time column.
    IllegalSchemaModificationError
        If the columns to remove contain all the feature columns.
    """
    table = super().remove_columns_with_missing_values()
    if self.time.name not in table.column_names:
        raise ColumnIsTimeError(self.time.name)
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            table,
            self.target.name,
            feature_names=sorted(
                set(self.features.column_names).intersection(set(table.column_names)),
                key={val: ix for ix, val in enumerate(self.features.column_names)}.__getitem__,
            ),
        ),
        time_name=self.time.name,
    )

remove_columns_with_non_numerical_values()

Return a new TimeSeries with every column that contains non-numerical values removed.

The original time series is not modified.

Returns:

Name Type Description
table TimeSeries

A time series without the columns that contain non-numerical values.

Raises:

Type Description
ColumnIsTargetError

If any of the columns to be removed is the target column.

ColumnIsTimeError

If any of the columns to be removed is the time column.

IllegalSchemaModificationError

If the columns to remove contain all the feature columns.

Source code in src/safeds/data/tabular/containers/_time_series.py
def remove_columns_with_non_numerical_values(self) -> TimeSeries:
    """
    Return a new `TimeSeries` with every column that contains non-numerical values removed.

    The original time series is not modified.

    Returns
    -------
    table : TimeSeries
        A time series without the columns that contain non-numerical values.

    Raises
    ------
    ColumnIsTargetError
        If any of the columns to be removed is the target column.
    ColumnIsTimeError
        If any of the columns to be removed is the time column.
    IllegalSchemaModificationError
        If the columns to remove contain all the feature columns.
    """
    table = super().remove_columns_with_non_numerical_values()
    if self.time.name not in table.column_names:
        raise ColumnIsTimeError(self.time.name)
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            table,
            self.target.name,
            feature_names=sorted(
                set(self.features.column_names).intersection(set(table.column_names)),
                key={val: ix for ix, val in enumerate(self.features.column_names)}.__getitem__,
            ),
        ),
        time_name=self.time.name,
    )

remove_duplicate_rows()

Return a new TimeSeries with all row duplicates removed.

The original time series is not modified.

Returns:

Name Type Description
result TimeSeries

The time series with the duplicate rows removed.

Source code in src/safeds/data/tabular/containers/_time_series.py
def remove_duplicate_rows(self) -> TimeSeries:
    """
    Return a new `TimeSeries` with all row duplicates removed.

    The original time series is not modified.

    Returns
    -------
    result : TimeSeries
        The time series with the duplicate rows removed.
    """
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            super().remove_duplicate_rows(),
            target_name=self.target.name,
            feature_names=self.features.column_names,
        ),
        time_name=self.time.name,
    )

remove_rows_with_missing_values()

Return a new TimeSeries without the rows that contain missing values.

The original time series is not modified.

Returns:

Name Type Description
table TimeSeries

A time series without the rows that contain missing values.

Source code in src/safeds/data/tabular/containers/_time_series.py
def remove_rows_with_missing_values(self) -> TimeSeries:
    """
    Return a new `TimeSeries` without the rows that contain missing values.

    The original time series is not modified.

    Returns
    -------
    table : TimeSeries
        A time series without the rows that contain missing values.
    """
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            super().remove_rows_with_missing_values(),
            target_name=self.target.name,
            feature_names=self.features.column_names,
        ),
        time_name=self.time.name,
    )

remove_rows_with_outliers()

Return a new TimeSeries with all rows that contain at least one outlier removed.

We define an outlier as a value that has a distance of more than 3 standard deviations from the column mean. Missing values are not considered outliers. They are also ignored during the calculation of the standard deviation.

The original time series is not modified.

Returns:

Name Type Description
new_time_series TimeSeries

A new time series without rows containing outliers.

Source code in src/safeds/data/tabular/containers/_time_series.py
def remove_rows_with_outliers(self) -> TimeSeries:
    """
    Return a new `TimeSeries` with all rows that contain at least one outlier removed.

    We define an outlier as a value that has a distance of more than 3 standard deviations from the column mean.
    Missing values are not considered outliers. They are also ignored during the calculation of the standard
    deviation.

    The original time series is not modified.

    Returns
    -------
    new_time_series : TimeSeries
        A new time series without rows containing outliers.
    """
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            super().remove_rows_with_outliers(),
            target_name=self.target.name,
            feature_names=self.features.column_names,
        ),
        time_name=self.time.name,
    )

rename_column(old_name, new_name)

Return a new TimeSeries with a single column renamed.

The original time series is not modified.

Parameters:

Name Type Description Default
old_name str

The old name of the column.

required
new_name str

The new name of the column.

required

Returns:

Name Type Description
table TimeSeries

The time series with the renamed column.

Raises:

Type Description
UnknownColumnNameError

If the specified old target column name does not exist.

DuplicateColumnNameError

If the specified new target column name already exists.

Source code in src/safeds/data/tabular/containers/_time_series.py
def rename_column(self, old_name: str, new_name: str) -> TimeSeries:
    """
    Return a new `TimeSeries` with a single column renamed.

    The original time series is not modified.

    Parameters
    ----------
    old_name : str
        The old name of the column.
    new_name : str
        The new name of the column.

    Returns
    -------
    table : TimeSeries
        The time series with the renamed column.

    Raises
    ------
    UnknownColumnNameError
        If the specified old target column name does not exist.
    DuplicateColumnNameError
        If the specified new target column name already exists.
    """
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            super().rename_column(old_name, new_name),
            target_name=new_name if self.target.name == old_name else self.target.name,
            feature_names=(
                self.features.column_names
                if old_name not in self.features.column_names
                else [
                    column_name if column_name != old_name else new_name
                    for column_name in self.features.column_names
                ]
            ),
        ),
        time_name=new_name if self.time.name == old_name else self.time.name,
    )

replace_column(old_column_name, new_columns)

Return a new TimeSeries with the specified old column replaced by a list of new columns.

If the column to be replaced is the target or time column, it must be replaced by exactly one column. That column becomes the new target or time column. If the column to be replaced is a feature column, the new columns that replace it all become feature columns.

The order of columns is kept. The original time series is not modified.

Parameters:

Name Type Description Default
old_column_name str

The name of the column to be replaced.

required
new_columns list[Column]

The new columns replacing the old column.

required

Returns:

Name Type Description
result TimeSeries

A time series with the old column replaced by the new columns.

Raises:

Type Description
UnknownColumnNameError

If the old column does not exist.

DuplicateColumnNameError

If the new column already exists and the existing column is not affected by the replacement.

ColumnSizeError

If the size of the column does not match the amount of rows.

IllegalSchemaModificationError

If the target or time column would be removed or replaced by more than one column.

Source code in src/safeds/data/tabular/containers/_time_series.py
def replace_column(self, old_column_name: str, new_columns: list[Column]) -> TimeSeries:
    """
    Return a new `TimeSeries` with the specified old column replaced by a list of new columns.

    If the column to be replaced is the target or time column, it must be replaced by exactly one column. That column
    becomes the new target or time column. If the column to be replaced is a feature column, the new columns that replace it
    all become feature columns.

    The order of columns is kept. The original time series is not modified.

    Parameters
    ----------
    old_column_name : str
        The name of the column to be replaced.
    new_columns : list[Column]
        The new columns replacing the old column.

    Returns
    -------
    result : TimeSeries
        A time series with the old column replaced by the new columns.

    Raises
    ------
    UnknownColumnNameError
        If the old column does not exist.
    DuplicateColumnNameError
        If the new column already exists and the existing column is not affected by the replacement.
    ColumnSizeError
        If the size of the column does not match the amount of rows.
    IllegalSchemaModificationError
        If the target or time column would be removed or replaced by more than one column.
    """
    if old_column_name == self.time.name:
        if len(new_columns) != 1:
            raise IllegalSchemaModificationError(
                f'Time column "{self.time.name}" can only be replaced by exactly one new column.',
            )
        else:
            return TimeSeries._from_tagged_table(
                TaggedTable._from_table(
                    super().replace_column(old_column_name, new_columns),
                    target_name=self.target.name,
                    feature_names=self.features.column_names,
                ),
                time_name=new_columns[0].name,
            )
    if old_column_name == self.target.name:
        if len(new_columns) != 1:
            raise IllegalSchemaModificationError(
                f'Target column "{self.target.name}" can only be replaced by exactly one new column.',
            )
        else:
            return TimeSeries._from_tagged_table(
                TaggedTable._from_table(
                    super().replace_column(old_column_name, new_columns),
                    target_name=new_columns[0].name,
                    feature_names=self.features.column_names,
                ),
                time_name=self.time.name,
            )
    else:
        return TimeSeries._from_tagged_table(
            TaggedTable._from_table(
                super().replace_column(old_column_name, new_columns),
                target_name=self.target.name,
                feature_names=(
                    self.features.column_names
                    if old_column_name not in self.features.column_names
                    else self.features.column_names[: self.features.column_names.index(old_column_name)]
                    + [col.name for col in new_columns]
                    + self.features.column_names[self.features.column_names.index(old_column_name) + 1 :]
                ),
            ),
            time_name=self.time.name,
        )

slice_rows(start=None, end=None, step=1)

Slice a part of the table into a new TimeSeries.

The original time series is not modified.

Parameters:

Name Type Description Default
start int | None

The first index of the range to be copied into a new time series, None by default.

None
end int | None

The last index of the range to be copied into a new time series, None by default.

None
step int

The step size used to iterate through the time series, 1 by default.

1

Returns:

Name Type Description
result TimeSeries

The resulting time series.

Raises:

Type Description
IndexOutOfBoundsError

If the index is out of bounds.

Source code in src/safeds/data/tabular/containers/_time_series.py
def slice_rows(
    self,
    start: int | None = None,
    end: int | None = None,
    step: int = 1,
) -> TimeSeries:
    """
    Slice a part of the table into a new `TimeSeries`.

    The original time series is not modified.

    Parameters
    ----------
    start : int | None
        The first index of the range to be copied into a new time series, None by default.
    end : int | None
        The last index of the range to be copied into a new time series, None by default.
    step : int
        The step size used to iterate through the time series, 1 by default.

    Returns
    -------
    result : TimeSeries
        The resulting time series.

    Raises
    ------
    IndexOutOfBoundsError
        If the index is out of bounds.
    """
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            super().slice_rows(start, end, step),
            target_name=self.target.name,
            feature_names=self.features.column_names,
        ),
        time_name=self.time.name,
    )

sort_columns(comparator=lambda , : col1.name > col2.name - col1.name < col2.name)

Sort the columns of a TimeSeries with the given comparator and return a new TimeSeries.

The comparator is a function that takes two columns col1 and col2 and returns an integer:

  • If the function returns a negative number, col1 will be ordered before col2.
  • If the function returns a positive number, col1 will be ordered after col2.
  • If the function returns 0, the original order of col1 and col2 will be kept.

If no comparator is given, the columns will be sorted alphabetically by their name.

The original time series is not modified.

Parameters:

Name Type Description Default
comparator Callable[[Column, Column], int]

The function used to compare two columns.

lambda , : name > name - name < name

Returns:

Name Type Description
new_time_series TimeSeries

A new time series with sorted columns.

Source code in src/safeds/data/tabular/containers/_time_series.py
def sort_columns(
    self,
    comparator: Callable[[Column, Column], int] = lambda col1, col2: (col1.name > col2.name)
    - (col1.name < col2.name),
) -> TimeSeries:
    """
    Sort the columns of a `TimeSeries` with the given comparator and return a new `TimeSeries`.

    The comparator is a function that takes two columns `col1` and `col2` and
    returns an integer:

    * If the function returns a negative number, `col1` will be ordered before `col2`.
    * If the function returns a positive number, `col1` will be ordered after `col2`.
    * If the function returns 0, the original order of `col1` and `col2` will be kept.

    If no comparator is given, the columns will be sorted alphabetically by their name.

    The original time series is not modified.

    Parameters
    ----------
    comparator : Callable[[Column, Column], int]
        The function used to compare two columns.

    Returns
    -------
    new_time_series : TimeSeries
        A new time series with sorted columns.
    """
    sorted_table = super().sort_columns(comparator)
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            sorted_table,
            target_name=self.target.name,
            feature_names=sorted(
                set(sorted_table.column_names).intersection(self.features.column_names),
                key={val: ix for ix, val in enumerate(sorted_table.column_names)}.__getitem__,
            ),
        ),
        time_name=self.time.name,
    )

transform_column(name, transformer)

Return a new TimeSeries with the provided column transformed by calling the provided transformer.

The original time series is not modified.

Returns:

Name Type Description
result TimeSeries

The time series with the transformed column.

Raises:

Type Description
UnknownColumnNameError

If the column does not exist.

Source code in src/safeds/data/tabular/containers/_time_series.py
def transform_column(self, name: str, transformer: Callable[[Row], Any]) -> TimeSeries:
    """
    Return a new `TimeSeries` with the provided column transformed by calling the provided transformer.

    The original time series is not modified.

    Returns
    -------
    result : TimeSeries
        The time series with the transformed column.

    Raises
    ------
    UnknownColumnNameError
        If the column does not exist.
    """
    return TimeSeries._from_tagged_table(
        TaggedTable._from_table(
            super().transform_column(name, transformer),
            target_name=self.target.name,
            feature_names=self.features.column_names,
        ),
        time_name=self.time.name,
    )