forked from TimelyDataflow/timely-dataflow
-
Notifications
You must be signed in to change notification settings - Fork 10
Expand file tree
/
Copy pathwordcount.rs
More file actions
68 lines (58 loc) · 2.65 KB
/
Copy pathwordcount.rs
File metadata and controls
68 lines (58 loc) · 2.65 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
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
use std::collections::HashMap;
use timely::dataflow::{InputHandle, ProbeHandle};
use timely::dataflow::operators::{Map, Operator, Inspect, Probe};
use timely::dataflow::channels::pact::Exchange;
fn main() {
// initializes and runs a timely dataflow.
timely::execute_from_args(std::env::args(), |worker| {
let mut input = InputHandle::new();
let probe = ProbeHandle::new();
// define a distribution function for strings.
let exchange = Exchange::new(|x: &(String, i64)| (x.0).len() as u64);
// create a new input, exchange data, and inspect its output
worker.dataflow::<usize,_,_>(|scope| {
input.to_stream(scope)
.container::<Vec<_>>()
.flat_map(|(text, diff): (String, i64)|
text.split_whitespace()
.map(move |word| (word.to_owned(), diff))
.collect::<Vec<_>>()
)
.container::<Vec<_>>()
.unary_frontier(exchange, "WordCount", |_capability, _info| {
let mut queues = HashMap::new();
let mut counts = HashMap::new();
move |(input, frontier), output| {
input.for_each_time(|time, data| {
queues.entry(time.retain())
.or_insert(Vec::new())
.extend(data.map(std::mem::take));
});
for (key, val) in queues.iter_mut() {
if !frontier.less_equal(key.time()) {
let mut session = output.session(key);
for mut batch in val.drain(..) {
for (word, diff) in batch.drain(..) {
let entry = counts.entry(word.clone()).or_insert(0i64);
*entry += diff;
session.give((word, *entry));
}
}
}
}
queues.retain(|_key, val| !val.is_empty());
}})
.container::<Vec<_>>()
.inspect(|x| println!("seen: {:?}", x))
.probe_with(&probe);
});
// introduce data and watch!
for round in 0..10 {
input.send(("round".to_owned(), 1));
input.advance_to(round + 1);
while probe.less_than(input.time()) {
worker.step();
}
}
}).unwrap();
}