C++ 不允许带有负索引的向量?

Posted

技术标签:

【中文标题】C++ 不允许带有负索引的向量?【英文标题】:C++ does not allow vector with negative index? 【发布时间】:2017-03-26 09:01:21 【问题描述】:

我试图创建一些带有负索引的向量,但刚刚得知它在 C++ 中是不允许的。是否有任何替代或更好的方法来做到这一点?

例如我想创建一个名为 Wt 的 3D 矢量:

在 VBA 上下文数组中是这样构建的:简单而漂亮

Redim Wt(0 to k_max,-i_max to i_max,-j_max to j_max)
' and use it like below for example: 
Wt(3, -100, -105) = .....

在 C++ 上下文中,它既不友好又不方便:

// resizing the vector:
Wt.resize(k_max + 1);
for (int k = 0; k < k_max + 1; k++) 
    Wt[k].resize(2 * i_max + 1);
    for (int i = 0; i < 2 * i_max + 1; i++) 
        Wt[k][i].resize(2 * j_max + 1);
    


// when using the vector:
for (int k = 0; k <= k_max; k++) 
    for (int i = -i_max; i <= i_max; i++) 
        for (int j = -j_max; j <= j_max; j++) 
            Wt[k][i + i_max][j + j_max] = ...
        
    

【问题讨论】:

负索引是什么意思? 一般你写一个类,把不友好和不方便的功能封装起来,给你想要的接口。 Are negative array indexes allowed in C?的可能重复 @Alex:我的意思是矢量,例如Wt[-1][-5][-100] = 1.235 ,其中索引 -1, -5, -100 都是负数... @TsuiJohn 我正好问你是否有矩阵,负索引是什么意思?它指向什么? 【参考方案1】:

不,您需要自己移动索引或实现一个为您移动它的类。如果需要,这里是代码

#include <iostream>
#include<vector>
#include <stdexcept>
using namespace std;


class FriendlyArray
    int _maxIndex;
    int _minIndex;
    vector<int> _data;
    public:
        FriendlyArray(int minIndex, int maxIndex)
        
            _maxIndex=maxIndex;
            _minIndex=minIndex;
            _data=vector<int>(_maxIndex-_minIndex+1);
        
    public:
      int& operator[] (int x) 
          if (x<_minIndex || x> _maxIndex)
            throw std::logic_error( "Exception example" ); 
          else 
              return _data[x-_minIndex];
          
       
;

int main() 
    FriendlyArray example(-1,11);
    example[-1]=4;
    cout<<example[-1]<<endl;
    // your code goes here
    return 0;

输出:4,如预期的那样

如果你想要一个更通用的版本,你会得到

#include <iostream>
#include<vector>
#include <stdexcept>
#include <assert.h>
using namespace std;


template<typename T> class FriendlyArray
    const int _maxIndex;
    const int _minIndex;
    vector<T> _data;
    public:
        FriendlyArray(int minIndex, int maxIndex):
        _minIndex(minIndex),
        _maxIndex(maxIndex)
        
            _data=vector<T>(_maxIndex-_minIndex+1);
        
    public:
      T& operator[] (int x)
          assert(!(x<_minIndex || x> _maxIndex));
          return _data[x-_minIndex];
       
;

int main() 
    FriendlyArray<int> example(-1,11);
    example[-1]=4;
    cout<<example[-1]<<endl;

    FriendlyArray<double> example2(-2,20);
    example2[-2]=0.5;
    cout<<example2[-2];
    return 0;

输出(如预期): 4 0.5

【讨论】:

好主意,但执行有一些错误。避免using namespace std,并使用初始化列表而不是赋值。可能已经包含了一些不错的东西:const 重载 operator[] 并且可能是模板参数而不是硬编码 int。就个人而言,我也会 assert 而不是 throw。从好的方面来说,您可以使用 int 来代替无符号类型的索引。 好的,会的。我想通过避免模板来展示这个想法,即使这样更灵活 请注意,任何支持数组中灵活索引的编译器都会在内部翻译索引。所以最终的代码或多或少都一样。 同样对于多维数组,赋值运算符的语法是什么?我们可以使用 int operator[]= (int x, int y) 来表示为 Wt[k][i][j] 分配某个值,例如= 1.1234? 多维不是问题,因为您分配数组的数组,就像以前一样

以上是关于C++ 不允许带有负索引的向量?的主要内容,如果未能解决你的问题,请参考以下文章

Rcpp R 向量大小限制(不允许负长度向量)

C++:为向量中的非连续索引赋值?

For-Loop一个带有负迭代器的“空”向量?

线框图(格子包)中的负长度向量是啥意思?

带有结构的 C++ 向量不起作用?

带有列的 C++ 文本文件到 2D 向量中