Skip to content

Commit 72a91bc

Browse files
updated threadpool and examples
1 parent b158709 commit 72a91bc

File tree

14 files changed

+123
-223
lines changed

14 files changed

+123
-223
lines changed

CMakeLists.txt

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -156,9 +156,6 @@ target_link_libraries(dynamic_traversal ${PROJECT_NAME} Threads::Threads)
156156
add_executable(framework ${TF_EXAMPLE_DIR}/framework.cpp)
157157
target_link_libraries(framework ${PROJECT_NAME} Threads::Threads)
158158

159-
add_executable(framework_dynamic_tasking ${TF_EXAMPLE_DIR}/framework_dynamic_tasking.cpp)
160-
target_link_libraries(framework_dynamic_tasking ${PROJECT_NAME} Threads::Threads)
161-
162159
endif()
163160

164161
# -----------------------------------------------------------------------------

docs/cookbook/Chapter6.dox

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -101,7 +101,7 @@ class MyExecutor { // closure type C, callable on operator ()
101101
template <typename... ArgsT>
102102
void emplace(ArgsT&&...); // arguments to construct the closure C
103103
template <typename C>
104-
void batch(std::vector<C>&&); // a vector of closures for batch insertions
104+
void batch(std::vector<C>&); // a vector of closures for batch insertions
105105
};
106106
using MyTaskflow = tf::BasicTaskflow<MyExecutor>;
107107
@endcode

docs/releases/master-branch.dox

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,8 @@ To download the newest version of Cpp-Taskflow, please clone from <a href="https
1616

1717
@li Improving the performance of tf::WorkStealingThreadpool.
1818
@li Enhancing the framework's reusability.
19-
19+
@li Replacing the move reference with l-value reference in batch inerstion of threadpools
20+
@li Adding a subflow function to examples/taskflow.cpp
2021

2122
@section master-branch_bug_fixes Bug Fixes
2223

example/dynamic_traversal.cpp

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
1+
// 2019/02/15 - modified by Tsung-Wei Huang
2+
// - refactored the code
3+
//
14
// 2019/01/03 - created by Chun-Xun Lin
2-
// - TODO:
3-
// 1. refactored the code (80-100 cols)
4-
// 2. parameterized the arguments
5+
// - use dynamic tasking to implement graph traversal
56

67
#include <taskflow/taskflow.hpp>
78
#include <random>
@@ -29,7 +30,9 @@ void traverse(Node* n, tf::SubflowBuilder& subflow) {
2930
for(size_t i=0; i<n->successors.size(); i++) {
3031
if(--(n->successors[i]->dependents) == 0) {
3132
n->successors[i]->level = n->level + 1;
32-
subflow.emplace([s=n->successors[i]](tf::SubflowBuilder &subflow){ traverse(s, subflow); });
33+
subflow.emplace([s=n->successors[i]](tf::SubflowBuilder &subflow){
34+
traverse(s, subflow);
35+
});
3336
}
3437
}
3538
}
@@ -49,7 +52,9 @@ void sequential_traversal(std::vector<Node*>& src) {
4952
}
5053
}
5154
auto end = std::chrono::system_clock::now();
52-
std::cout << "Seq runtime: " << std::chrono::duration_cast<std::chrono::milliseconds>(end - start).count() << '\n';
55+
std::cout << "Seq runtime: "
56+
<< std::chrono::duration_cast<std::chrono::milliseconds>(end - start).count()
57+
<< '\n';
5358
}
5459

5560
void tf_traversal(std::vector<Node*>& src) {

example/framework.cpp

Lines changed: 10 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
1+
// 2019/02/15 - modified by Tsung-Wei Huang
2+
// - refactored the code
3+
//
14
// 2019/01/17 - created by Chun-Xun
2-
// - added example of using the Framework
5+
// - added example of using the Framework
36

47
#include <taskflow/taskflow.hpp>
58

@@ -27,12 +30,11 @@ int main(){
2730

2831
std::cout << "Run the framework once without callback\n";
2932

30-
std::cout << "Dump before execution:\n";
33+
std::cout << "Dump the framework before execution:\n";
3134
f.dump(std::cout);
3235
std::cout << std::endl;
3336

34-
auto future = tf.run(f);
35-
future.get();
37+
tf.run(f).get();
3638
std::cout << std::endl;
3739

3840
std::cout << "Dump after execution:\n";
@@ -44,29 +46,14 @@ int main(){
4446
tf.wait_for_all();
4547
std::cout << std::endl;
4648

47-
std::cout << "Execute the framework 2 times without a callback\n";
49+
std::cout << "Execute the framework two times without a callback\n";
4850
tf.run_n(f, 2).get();
49-
std::cout << "Dump after 2 executions:\n";
51+
std::cout << "Dump after two executions:\n";
5052
tf.dump_topologies(std::cout);
5153
std::cout << std::endl;
5254

53-
std::cout << "Execute the framework 4 times with a callback\n";
54-
tf.run_n(f, 4, [] () mutable { std::cout << "The framework finishes\n"; }).get();
55-
std::cout << std::endl;
56-
57-
std::cout << "Silently run the framework\n";
58-
tf.run(f);
59-
tf.wait_for_all();
60-
std::cout << std::endl;
61-
62-
std::cout << "Silently run the framework 2 times \n";
63-
tf.run_n(f, 2);
64-
tf.wait_for_all();
65-
std::cout << std::endl;
66-
67-
std::cout << "Silently run the framework with callback\n";
68-
tf.run_n(f, 1, []() { std::cout << "The framework finishes\n"; });
69-
tf.wait_for_all();
55+
std::cout << "Execute the framework four times with a callback\n";
56+
tf.run_n(f, 4, [] () { std::cout << "The framework finishes\n"; }).get();
7057
std::cout << std::endl;
7158

7259
std::cout << "Run the framework until a counter (init value=3) becomes zero\n";

example/framework_dynamic_tasking.cpp

Lines changed: 0 additions & 173 deletions
This file was deleted.

example/taskflow.cpp

Lines changed: 66 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,7 @@
1+
// 2019/02/20 - modified by Tsung-Wei Huang
2+
// - added empty_subflow benchmarks
3+
// - added steady_subflow benchmarks
4+
//
15
// 2018/12/04 - modified by Tsung-Wei Huang
26
// - replaced privatized threadpool with work stealing threadpool
37
//
@@ -16,7 +20,7 @@
1620
#include <climits>
1721
#include <iomanip>
1822

19-
constexpr int WIDTH = 12;
23+
constexpr int WIDTH = 15;
2024

2125
// Procedure: benchmark
2226
#define BENCHMARK(TITLE, F) \
@@ -340,6 +344,65 @@ auto multiple_dispatches() {
340344
return std::chrono::duration_cast<std::chrono::milliseconds>(end - beg).count();
341345
}
342346

347+
// ============================================================================
348+
// Nested subflow
349+
// ============================================================================
350+
351+
// Function: empty_subflow
352+
template <typename T>
353+
auto empty_subflow() {
354+
355+
std::function<void(tf::SubflowBuilder&, uint64_t)> grow;
356+
357+
grow = [&grow] (tf::SubflowBuilder& subflow, uint64_t depth) {
358+
if(depth < 20) {
359+
subflow.emplace(
360+
[depth, &grow](tf::SubflowBuilder& subsubflow){ grow(subsubflow, depth+1); },
361+
[depth, &grow](tf::SubflowBuilder& subsubflow){ grow(subsubflow, depth+1); });
362+
subflow.detach();
363+
}
364+
};
365+
366+
auto beg = std::chrono::high_resolution_clock::now();
367+
368+
{
369+
T tf;
370+
tf.emplace([&] (tf::SubflowBuilder& subflow) { grow(subflow, 0); });
371+
tf.wait_for_all();
372+
}
373+
374+
auto end = std::chrono::high_resolution_clock::now();
375+
return std::chrono::duration_cast<std::chrono::milliseconds>(end - beg).count();
376+
}
377+
378+
// Function: steady_subflow
379+
template <typename T>
380+
auto steady_subflow() {
381+
382+
std::function<void(tf::SubflowBuilder&, uint64_t)> grow;
383+
384+
grow = [&grow] (tf::SubflowBuilder& subflow, uint64_t depth) {
385+
std::this_thread::sleep_for(std::chrono::milliseconds(100));
386+
if(depth < 3) {
387+
subflow.emplace(
388+
[depth, &grow](tf::SubflowBuilder& subsubflow){ grow(subsubflow, depth+1); },
389+
[depth, &grow](tf::SubflowBuilder& subsubflow){ grow(subsubflow, depth+1); });
390+
subflow.detach();
391+
}
392+
};
393+
394+
auto beg = std::chrono::high_resolution_clock::now();
395+
396+
{
397+
T tf;
398+
tf.emplace([&] (tf::SubflowBuilder& subflow) { grow(subflow, 0); });
399+
tf.wait_for_all();
400+
}
401+
402+
auto end = std::chrono::high_resolution_clock::now();
403+
return std::chrono::duration_cast<std::chrono::milliseconds>(end - beg).count();
404+
}
405+
343406
// ----------------------------------------------------------------------------
344407

345408
// Function: main
@@ -360,6 +423,8 @@ int main(int argc, char* argv[]) {
360423
BENCHMARK("linear", linear_graph);
361424
BENCHMARK("dag", level_graph);
362425
BENCHMARK("dynamic", dynamic_stem);
426+
BENCHMARK("empty-subflow", empty_subflow);
427+
BENCHMARK("steady-subflow", steady_subflow);
363428

364429

365430
return 0;

0 commit comments

Comments
 (0)