代码之家  ›  专栏  ›  技术社区  ›  kesarling

使整个对象保持不变与使整个对象和内部对象保持不变是一样的吗?

  •  0
  • kesarling  · 技术社区  · 5 年前

    简言之,问题是以下两种说法是否相等:

    const std::vector<std::vector<int>>
    

    const std::vector<const std::vector<int>>
    

    因为,在下面的两个代码中,第一个没有编译!

    code1

    #include <vector>
    
    long findMaxSum(const std::vector<const std::vector<int>>& vecs) {
    
    }
    
    int main() {
        std::vector<std::vector<int>> stacks(10,std::vector<int>(10)); //yeah yeah I know stacks is evil!
        for (auto& stack : stacks) {
            for (auto& elem : stack) {
                elem = 4;
            }
        }
        auto t = findMaxSum(stacks);
        return 0;
    }
    

    code2

    #include <vector>
    
    long findMaxSum(const std::vector<std::vector<int>>& vecs) {
    
    }
    
    int main() {
        std::vector<std::vector<int>> stacks(10,std::vector<int>(10));
        for (auto& stack : stacks) {
            for (auto& elem : stack) {
                elem = 4;
            }
        }
        auto t = findMaxSum(stacks);
        return 0;
    }
    
    0 回复  |  直到 5 年前
        1
  •  2
  •   Jerry Coffin    5 年前

    它们不太一样,但你真的没什么办法。

    正如您所发现的,尝试创建 vector const 通常会失败。

    你可以把外面的收藏品 std::array --它对所包含的元素没有严格的要求,所以 std::array<const std::vector<whatever>, SIZE>

    // receive a vector of pointers to const vectors:
    int findMaxSum(std::vector<const std::vector<int> *> &outer) {
        std::vector<int> sums;
        std::transform(outer.begin(), outer.end(), 
            std::back_inserter(sums), 
            [](auto v) { return std::accumulate(v->begin(), v->end(), 0); });
    
        return *std::max_element(sums.begin(), sums.end());
    }
    
    int main() { 
        const std::vector<int> a {1, 2};
        const std::vector<int> b {3, 4};
    
        // pass only the address of each of the component vectors:
        std::vector<const std::vector<int> *> c { &a, &b};
        std::cout << findMaxSum(c) << "\n";
    }
    

    这样做还有一个额外的优点,即避免复制每个分量向量只是为了将其传递给函数。如果分量向量很大,这可以是一个重要的考虑因素。