Skip to content
Snippets Groups Projects
Commit 9a5dca21 authored by Enrico Guiraud's avatar Enrico Guiraud Committed by Enric Tejedor Saavedra
Browse files

[TreeProcMT] Add nThreads argument to all constructors

...and add a test.

The new argument is to make TTreeProcessorMT consistent with other
multi-threading interfaces, namely TThreadExecutor. This is the last
ingredient required to fix ROOT-10561.
parent 74b9eb67
No related branches found
No related tags found
No related merge requests found
...@@ -99,10 +99,11 @@ private: ...@@ -99,10 +99,11 @@ private:
static unsigned int fgMaxTasksPerFilePerWorker; static unsigned int fgMaxTasksPerFilePerWorker;
public: public:
TTreeProcessorMT(std::string_view filename, std::string_view treename = ""); TTreeProcessorMT(std::string_view filename, std::string_view treename = "", UInt_t nThreads = 0u);
TTreeProcessorMT(const std::vector<std::string_view> &filenames, std::string_view treename = ""); TTreeProcessorMT(const std::vector<std::string_view> &filenames, std::string_view treename = "",
TTreeProcessorMT(TTree &tree, const TEntryList &entries); UInt_t nThreads = 0u);
TTreeProcessorMT(TTree &tree); TTreeProcessorMT(TTree &tree, const TEntryList &entries, UInt_t nThreads = 0u);
TTreeProcessorMT(TTree &tree, UInt_t nThreads = 0u);
void Process(std::function<void(TTreeReader &)> func); void Process(std::function<void(TTreeReader &)> func);
static void SetMaxTasksPerFilePerWorker(unsigned int m); static void SetMaxTasksPerFilePerWorker(unsigned int m);
......
...@@ -416,9 +416,11 @@ std::vector<std::string> TTreeProcessorMT::FindTreeNames() ...@@ -416,9 +416,11 @@ std::vector<std::string> TTreeProcessorMT::FindTreeNames()
/// \param[in] filename Name of the file containing the tree to process. /// \param[in] filename Name of the file containing the tree to process.
/// \param[in] treename Name of the tree to process. If not provided, the implementation will search /// \param[in] treename Name of the tree to process. If not provided, the implementation will search
/// for a TTree key in the file and will use the first one it finds. /// for a TTree key in the file and will use the first one it finds.
TTreeProcessorMT::TTreeProcessorMT(std::string_view filename, std::string_view treename) /// \param[in] nThreads Number of threads to create in the underlying thread-pool. The semantics of this argument are
/// the same as for TThreadExecutor.
TTreeProcessorMT::TTreeProcessorMT(std::string_view filename, std::string_view treename, UInt_t nThreads)
: fFileNames({std::string(filename)}), : fFileNames({std::string(filename)}),
fTreeNames(treename.empty() ? FindTreeNames() : std::vector<std::string>{std::string(treename)}), fFriendInfo() fTreeNames(treename.empty() ? FindTreeNames() : std::vector<std::string>{std::string(treename)}), fFriendInfo(), fPool(nThreads)
{ {
} }
...@@ -439,15 +441,18 @@ std::vector<std::string> CheckAndConvert(const std::vector<std::string_view> &vi ...@@ -439,15 +441,18 @@ std::vector<std::string> CheckAndConvert(const std::vector<std::string_view> &vi
/// \param[in] filenames Collection of the names of the files containing the tree to process. /// \param[in] filenames Collection of the names of the files containing the tree to process.
/// \param[in] treename Name of the tree to process. If not provided, the implementation will /// \param[in] treename Name of the tree to process. If not provided, the implementation will
/// search filenames for a TTree key and will use the first one it finds in each file. /// search filenames for a TTree key and will use the first one it finds in each file.
/// \param[in] nThreads Number of threads to create in the underlying thread-pool. The semantics of this argument are
/// the same as for TThreadExecutor.
/// ///
/// If different files contain TTrees with different names and automatic TTree name detection is not an option /// If different files contain TTrees with different names and automatic TTree name detection is not an option
/// (for example, because some of the files contain multiple TTrees) please manually create a TChain and pass /// (for example, because some of the files contain multiple TTrees) please manually create a TChain and pass
/// it to the appropriate TTreeProcessorMT constructor. /// it to the appropriate TTreeProcessorMT constructor.
TTreeProcessorMT::TTreeProcessorMT(const std::vector<std::string_view> &filenames, std::string_view treename) TTreeProcessorMT::TTreeProcessorMT(const std::vector<std::string_view> &filenames, std::string_view treename,
UInt_t nThreads)
: fFileNames(CheckAndConvert(filenames)), : fFileNames(CheckAndConvert(filenames)),
fTreeNames(treename.empty() ? FindTreeNames() fTreeNames(treename.empty() ? FindTreeNames()
: std::vector<std::string>(fFileNames.size(), std::string(treename))), : std::vector<std::string>(fFileNames.size(), std::string(treename))),
fFriendInfo() fFriendInfo(), fPool(nThreads)
{ {
} }
...@@ -481,16 +486,22 @@ std::vector<std::string> GetFilesFromTree(TTree &tree) ...@@ -481,16 +486,22 @@ std::vector<std::string> GetFilesFromTree(TTree &tree)
/// Constructor based on a TTree and a TEntryList. /// Constructor based on a TTree and a TEntryList.
/// \param[in] tree Tree or chain of files containing the tree to process. /// \param[in] tree Tree or chain of files containing the tree to process.
/// \param[in] entries List of entry numbers to process. /// \param[in] entries List of entry numbers to process.
TTreeProcessorMT::TTreeProcessorMT(TTree &tree, const TEntryList &entries) /// \param[in] nThreads Number of threads to create in the underlying thread-pool. The semantics of this argument are
/// the same as for TThreadExecutor.
TTreeProcessorMT::TTreeProcessorMT(TTree &tree, const TEntryList &entries, UInt_t nThreads)
: fFileNames(GetFilesFromTree(tree)), fTreeNames(GetTreeFullPaths(tree)), fEntryList(entries), : fFileNames(GetFilesFromTree(tree)), fTreeNames(GetTreeFullPaths(tree)), fEntryList(entries),
fFriendInfo(GetFriendInfo(tree)) fFriendInfo(GetFriendInfo(tree)), fPool(nThreads)
{ {
} }
//////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////
/// Constructor based on a TTree. /// Constructor based on a TTree.
/// \param[in] tree Tree or chain of files containing the tree to process. /// \param[in] tree Tree or chain of files containing the tree to process.
TTreeProcessorMT::TTreeProcessorMT(TTree &tree) : TTreeProcessorMT(tree, TEntryList()) {} /// \param[in] nThreads Number of threads to create in the underlying thread-pool. The semantics of this argument are
/// the same as for TThreadExecutor.
TTreeProcessorMT::TTreeProcessorMT(TTree &tree, UInt_t nThreads) : TTreeProcessorMT(tree, TEntryList(), nThreads)
{
}
////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////
/// Process the entries of a TTree in parallel. The user-provided function /// Process the entries of a TTree in parallel. The user-provided function
......
...@@ -387,3 +387,43 @@ TEST(TreeProcessorMT, ChainWithFriendChain) ...@@ -387,3 +387,43 @@ TEST(TreeProcessorMT, ChainWithFriendChain)
// Clean-up // Clean-up
DeleteFiles(fileNames); DeleteFiles(fileNames);
} }
TEST(TreeProcessorMT, SetNThreads)
{
ROOT::DisableImplicitMT();
EXPECT_EQ(ROOT::GetImplicitMTPoolSize(), 0u);
{
ROOT::TTreeProcessorMT p("somefile", "sometree", 1u);
EXPECT_EQ(ROOT::GetImplicitMTPoolSize(), 1u);
}
EXPECT_EQ(ROOT::GetImplicitMTPoolSize(), 0u);
{
ROOT::TTreeProcessorMT p({"somefile", "some_other"}, "sometree", 1u);
EXPECT_EQ(ROOT::GetImplicitMTPoolSize(), 1u);
}
{
// we need a file because in-memory trees are not supported
// (and are detected at TTreeProcessorMT construction time)
TFile f("treeprocmt_setnthreads.root", "recreate");
TTree t("t", "t");
t.Write();
TEntryList l;
ROOT::TTreeProcessorMT p(t, l, 1u);
EXPECT_EQ(ROOT::GetImplicitMTPoolSize(), 1u);
f.Close();
gSystem->Unlink("treeprocmt_setnthreads.root");
}
{
// we need a file because in-memory trees are not supported
// (and are detected at TTreeProcessorMT construction time)
TFile f("treeprocmt_setnthreads.root", "recreate");
TTree t("t", "t");
t.Write();
ROOT::TTreeProcessorMT p(t, 1u);
EXPECT_EQ(ROOT::GetImplicitMTPoolSize(), 1u);
gSystem->Unlink("treeprocmt_setnthreads.root");
}
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment