@@ -9,10 +9,13 @@ use crate::ExchangeData;
9
9
use crate :: order:: PartialOrder ;
10
10
11
11
/// A composite trait for types that serve as timestamps in timely dataflow.
12
+ ///
13
+ /// By implementing this trait, you promise that the type's [PartialOrder] implementation
14
+ /// is compatible with [Ord], such that if `a.less_equal(b)` then `a <= b`.
12
15
pub trait Timestamp : Clone +Eq +PartialOrder +Debug +Send +Any +ExchangeData +Hash +Ord {
13
16
/// A type summarizing action on a timestamp along a dataflow path.
14
17
type Summary : PathSummary < Self > + ' static ;
15
- /// A minimum value suitable as a default.
18
+ /// A unique minimum value in our partial order, suitable as a default.
16
19
fn minimum ( ) -> Self ;
17
20
}
18
21
@@ -28,14 +31,21 @@ pub trait PathSummary<T> : Clone+'static+Eq+PartialOrder+Debug+Default {
28
31
/// in computation, uses this method and will drop messages with timestamps that when advanced
29
32
/// result in `None`. Ideally, all other timestamp manipulation should behave similarly.
30
33
///
34
+ /// This summary's partial order is expected to be compatible with the partial order of [T],
35
+ /// in the sense that if `s1.less_equal(s2)`, then `s1.results_in(&t)` is less than or equal to
36
+ /// `s2.results_in(&t)`.
37
+ ///
38
+ /// Note that `Self::default()` is expected to behave as an "empty" or "noop" summary, such that
39
+ /// `Self::default().results_in(&t) == Some(t)`.
40
+ ///
31
41
/// # Examples
32
42
/// ```
33
43
/// use timely::progress::timestamp::PathSummary;
34
44
///
35
45
/// let timestamp = 3;
36
46
///
37
47
/// let summary1 = 5;
38
- /// let summary2 = usize::max_value() - 2;
48
+ /// let summary2 = usize::MAX - 2;
39
49
///
40
50
/// assert_eq!(summary1.results_in(×tamp), Some(8));
41
51
/// assert_eq!(summary2.results_in(×tamp), None);
@@ -49,14 +59,27 @@ pub trait PathSummary<T> : Clone+'static+Eq+PartialOrder+Debug+Default {
49
59
/// important that this not be used casually, as this does not prevent the actual movement of
50
60
/// data.
51
61
///
62
+ /// Calling `results_in` on the composed summary should behave the same as though the two
63
+ /// summaries were applied to the argument in order.
64
+ ///
52
65
/// # Examples
53
66
/// ```
54
67
/// use timely::progress::timestamp::PathSummary;
55
68
///
56
69
/// let summary1 = 5;
57
- /// let summary2 = usize::max_value() - 3;
70
+ /// let summary2 = usize::MAX - 3;
58
71
///
59
72
/// assert_eq!(summary1.followed_by(&summary2), None);
73
+ ///
74
+ /// let time = 10;
75
+ /// let summary2 = 15;
76
+ /// assert_eq!(
77
+ /// // Applying the composed summary...
78
+ /// summary1.followed_by(&summary2).and_then(|s| s.results_in(&time)),
79
+ /// // ...has the same result as applying the two summaries in sequence.
80
+ /// summary1.results_in(&time).and_then(|t| summary2.results_in(&t)),
81
+ /// );
82
+ ///
60
83
/// ```
61
84
fn followed_by ( & self , other : & Self ) -> Option < Self > ;
62
85
}
0 commit comments