在c ++中重构特定的嵌套循环

时间:2017-06-22 13:31:39

标签: c++ lambda nested-loops c++17

我正在使用一个不支持目录高级目录操作的c ++框架(ROOT),因此当我在文件中生成我的(相当复杂的)目录系统时,我通常最终会使用很多丑陋的嵌套for循环。我的问题是,是否有可能用较少的重复方法替换像这里所示的模式?使用lambda等接受其他lambdas作为参数的东西,或者任何东西(链接代码只是dir系统创建的一小部分)?

// Disk
t_outputFile -> cd("ROC_efficiency_disk_level_comparison");
gDirectory   -> mkdir(layerDirName);
for(std::size_t sideIndex = 0, maxSideIndex = sideNames.size(); sideIndex < maxSideIndex; ++sideIndex)
{
   const char* sideDirName = sideNames[sideIndex].c_str();
   t_outputFile -> cd("ROC_efficiency_disk_level_comparison");
   gDirectory -> cd(layerDirName);
   gDirectory -> mkdir(sideDirName);
   gDirectory -> cd(sideDirName);
   for(std::size_t diskIndex = 0, diskMaxIndex = diskNames.size(); diskIndex < diskMaxIndex; ++diskIndex)
   {
      const char* diskDirName = diskNames[diskIndex].c_str();
      t_outputFile -> cd("ROC_efficiency_disk_level_comparison");
      gDirectory -> cd(layerDirName);
      gDirectory -> cd(sideDirName);
      gDirectory -> mkdir(diskDirName);
   }
}
// Disk-ring
t_outputFile -> cd("ROC_efficiency_disk-ring_level_comparison");
gDirectory   -> mkdir(layerDirName);
for(std::size_t sideIndex = 0, maxSideIndex = sideNames.size(); sideIndex < maxSideIndex; ++sideIndex)
{
   const char* sideDirName = sideNames[sideIndex].c_str();
   t_outputFile -> cd("ROC_efficiency_disk-ring_level_comparison");
   gDirectory -> cd(layerDirName);
   gDirectory -> mkdir(sideDirName);
   gDirectory -> cd(sideDirName);
   for(std::size_t diskIndex = 0, diskMaxIndex = diskNames.size(); diskIndex < diskMaxIndex; ++diskIndex)
   {
      const char* diskDirName = diskNames[diskIndex].c_str();
      t_outputFile -> cd("ROC_efficiency_disk-ring_level_comparison");
      gDirectory -> cd(layerDirName);
      gDirectory -> cd(sideDirName);
      gDirectory -> mkdir(diskDirName);
      gDirectory -> cd(diskDirName);
      for(std::size_t ringIndex = 0, ringMaxIndex = ringNames.size(); ringIndex < ringMaxIndex; ++ringIndex)
      {
         const char* ringDirName = ringNames[ringIndex].c_str();
         t_outputFile -> cd("ROC_efficiency_disk-ring_level_comparison");
         gDirectory -> cd(layerDirName);
         gDirectory -> cd(sideDirName);
         gDirectory -> cd(diskDirName);
         gDirectory -> mkdir(ringDirName);
      }
   }
}
// Blade
t_outputFile -> cd("ROC_efficiency_blade_level_comparison");
gDirectory   -> mkdir(layerDirName);
for(std::size_t sideIndex = 0, maxSideIndex = sideNames.size(); sideIndex < maxSideIndex; ++sideIndex)
{
   const char* sideDirName = sideNames[sideIndex].c_str();
   t_outputFile -> cd("ROC_efficiency_blade_level_comparison");
   gDirectory -> cd(layerDirName);
   gDirectory -> mkdir(sideDirName);
   gDirectory -> cd(sideDirName);
   for(std::size_t diskIndex = 0, diskMaxIndex = diskNames.size(); diskIndex < diskMaxIndex; ++diskIndex)
   {
      const char* diskDirName = diskNames[diskIndex].c_str();
      t_outputFile -> cd("ROC_efficiency_blade_level_comparison");
      gDirectory -> cd(layerDirName);
      gDirectory -> cd(sideDirName);
      gDirectory -> mkdir(diskDirName);
      gDirectory -> cd(diskDirName);
      for(std::size_t ringIndex = 0, ringMaxIndex = ringNames.size(); ringIndex < ringMaxIndex; ++ringIndex)
      {
         const char* ringDirName = ringNames[ringIndex].c_str();
         t_outputFile -> cd("ROC_efficiency_blade_level_comparison");
         gDirectory -> cd(layerDirName);
         gDirectory -> cd(sideDirName);
         gDirectory -> cd(diskDirName);
         gDirectory -> mkdir(ringDirName);
         gDirectory -> cd(ringDirName);
         for(std::size_t bladeIndex = 0, bladeMaxIndex = bladeNames.size(); bladeIndex < bladeMaxIndex; ++bladeIndex)
         {
            const char* bladeDirName = bladeNames[bladeIndex].c_str();
            t_outputFile -> cd("ROC_efficiency_blade_level_comparison");
            gDirectory -> cd(layerDirName);
            gDirectory -> cd(sideDirName);
            gDirectory -> cd(diskDirName);
            gDirectory -> cd(ringDirName);
            gDirectory -> mkdir(bladeDirName);
         }
      }
   }
}

对此操作的易于理解的解释:它返回到文件中的根目录,然后在那里创建许多目录,每个目录包含相同的子目录系统。案例的深度不同,每次创建新的子目录时,程序都必须首先返回根目录。

示例:

├── FPix/
│   ├── Positive_Side
│   │   ├─ Disk_1
│   │   │   ├─ Ring_1
│   │   │   │   └─ Some_other_nested_levels
│   │   │   └─ Ring_2
│   │   │       └─ Some_other_nested_levels
│   │   ├─ Disk_2
│   │   │   ├─ Ring_1
│   │   │   │   └─ Some_other_nested_levels
│   │   │   └─ Ring_2
│   │   │      └─ Some_other_nested_levels
│   │   └─ ...
│   │       └─ Same_as_the_other_disks
│   │
│   └── Negative_side
│        └─ Same_as_the_positive_side
│
├── ROC_efficiency_disk_level_comparison
│   └─ The_nesting_here_only_goes_until_disks
│        └─ ...
│
├── ROC_efficiency_ring_level_comparison
│   └─ The_nesting_here_only_goes_until_rings
│        └─ ...
│
└── Many_many_other_directories_that_have_the_same_dirs_but_different_levels_of_nesting

1 个答案:

答案 0 :(得分:0)

您可以定义已作为树发布的示例结构,其中根目录为根,子文件夹为节点,这些目录的子目录为这些节点的节点等(直到您到达目录的末尾)结构体)。 然后你可以做类似

的事情

function checkOdd(num) { num = Math.abs(num); if(num==0) return false; else if(num==1) return true; else return checkOdd(num-2); }

假设您正确定义了树,那将生成整个结构。

编辑:我刚刚意识到我发布了python代码而你正在使用C ++,但我相信你会得到一般的想法。