【问题标题】:How to avoid repeating myself in nested loops如何避免在嵌套循环中重复自己
【发布时间】:2019-04-28 02:56:41
【问题描述】:

我有一个嵌套循环的方法,如下所示,我在其中做了一些计算上昂贵的东西和一些计算上便宜的东西:

for(int i = 0; i < SIZE_I; ++i) {
    // Do cheap stuff 1
    // Do computationally expensive stuff 1
    for(int j = 0; j < SIZE_J; ++j) {
        // Do cheap stuff 2
        // Do computationally expensive stuff 2
        for(int k = 0; k < SIZE_K; ++k) {
            // Do cheap stuff 3
            // Do computationally expensive stuff 3
        }
    }
}

目前,我调用我的方法一次。但我需要将便宜的东西与昂贵的东西分开。问题是如果我开发两种方法,我将需要重复嵌套循环和大量与它们纠缠的代码。

我想知道是否有最佳实践或工具可以帮助我将我的单一方法分成两种方法,而无需重复大量代码。或者,如果有一种解决方案可以将廉价与昂贵分开,而无需将我的单一方法分解为两种方法?

【问题讨论】:

  • 为什么不能使用 lambda 表达式?
  • 什么?你能举一个真实的例子吗?我猜你的问题要读两遍才能理解。
  • 为什么不把每个代码块放到自己的函数中呢?这几乎就是函数的用途。
  • 没有人提到 cough 是函数的布尔参数,cough 是默认值,还有一些 if 围绕着昂贵的东西......
  • @Bathsheba 您是否经常使用长度 >32767 但 ptrdiff_t。

标签: c++


【解决方案1】:

我最终这样做了:

enum CallStatus {
    CallStatus_Cheap = 0,
    CallStatus_Expensive
};

bool MyClass::MyMethod(MyClass::CallStatus callStatus)
{
    for(int i = 0; i < SIZE_I; ++i) {

        switch (callStatus) {
        case MyClass::CallStatus_Cheap:
            // Do cheap stuff 1
            break;
        case MyClass::CallStatus_Expensive:
            // Do computationally expensive stuff 1
            break;
        default:
            break;
        }

        for(int j = 0; j < SIZE_J; ++j) {

            switch (callStatus) {
            case MyClass::CallStatus_Cheap:
                // Do cheap stuff 2
                break;
            case MyClass::CallStatus_Expensive:
                // Do computationally expensive stuff 2
                break;
            default:
                break;
            }

            for(int k = 0; k < SIZE_K; ++k) {

                switch (callStatus) {
                case MyClass::CallStatus_Cheap:
                    // Do cheap stuff 3
                    break;
                case MyClass::CallStatus_Expensive:
                    // Do computationally expensive stuff 3
                    break;
                default:
                    break;
                }

            }
        }
    }

// ...

}

使用enum 作为参数/参数和switch,现在我可以分别做便宜昂贵的东西,即使它们非常纠缠在嵌套循环中。

【讨论】:

  • 顺便说一句,如果您发现您的switch 语句太昂贵,您可以将您的CallStatus 参数转换为模板参数。
  • @anatolyg 谢谢! :)
【解决方案2】:

您可以创建一个以函数或 lambda 表达式作为参数的函数。 它会执行嵌套循环并应用您作为参数传递的“便宜的东西”或“昂贵的东西”。

您可以将其称为“便宜的东西”一次,然后将其称为“昂贵的东西”。

【讨论】:

  • 我没想到要使用 lambda。我试试看
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-12-26
  • 1970-01-01
  • 2012-06-25
  • 1970-01-01
  • 2021-08-19
相关资源
最近更新 更多