草庐IT

C++中vector<vector<int> >的用法

Ashley zhao 2024-07-16 原文

注意vector<vector<int> >后面的尖括号前面要加上空格,否则在有些编译器出现问题

vector<vector<int>> A;//错误的定义方式
vector<vector<int> > A;//正确的定义方式

一、为什么是vector?

对于数组,大家常用索引和指针来操作数组,给程序设计带来了很大的灵活性。但是数组的越界可能会引起程序的崩溃,而且动态性不好,包括动态改变大小,动态申请。有什么办法可以解决这些问题吗?
关于vector我不想多说,我假设大家都了解temlplate 和 STL比如map、list、vector等)。 学习C++的时候学到过STL(标准模板库)知道vector提供了operator[]函数。可以像数组一样的操作,而且还有边界检查,动态改变大小。vector本来就是可以用来代替一维数组的,vector提供了operator[]函数,可以像数组一样的操作,而且还有边界检查,动态改变大小。这里只介绍用它来代替二维的数组,二维以上的可以依此类推。
vector<vector<int> > array2(3);

   array2可以保存3个向量,向量的长度是可以改变的。array2[i]返回的是第i个向量。同理,array2[i][j]返回的是第i个向量中的第j个元素。
   vector<vector<int>  > array2(3);
   array2[1][2]=9;

我保证你的程序会segement failed,原因就是你没有指定向量的大小。用push_back函数可以解决问题,如下:

for(int i=0;i<3;i++)
   array2[i].resize(3);//就定义了一个3X3的数组了(另一个3在 申明时定义的)。而且你可以随时改变它的大小

二、什么是vector?

向量(Vector)是一个封装了动态大小数组的顺序容器(Sequence Container)。跟任意其它类型容器一样,它能够存放各种类型的对象。可以简单的认为,向量是一个能够存放任意类型动态数组

2.0 容器特性

1)顺序序列
顺序容器中的元素按照严格的线性顺序排序。可以通过元素在序列中的位置访问对应的元素。
2)动态数组
支持对序列中的任意元素进行快速直接访问,甚至可以通过指针算述进行该操作。操供了在序列末尾相对快速地添加/删除元素的操作。
3)能够感知内存分配器的
容器使用一个内存分配器对象来动态地处理它的存储需求。

2.1. 基本操作

a. 头文件#include<vector>
b. 创建vector对象:vector dp;
c. 尾部插入数字:vec.push_back(a);
d. 使用下标访问元素,cout<<dp[0]<<endl;记住下标是从0开始的。
使用迭代器访问元素.
vector::iterator it;
for(it=vec.begin();it!=vec.end();it++) cout<<*it<<endl;

e. 插入元素: vec.insert(vec.begin()+i,a);在第i个元素后面插入a;
f. 删除元素: vec.erase(vec.begin()+2);删除第3个元素
vec.erase(vec.begin()+i,vec.end()+j);删除区间[i,j-1];区间从0开始
h. 向量大小:vec.size();
g. 清空:vec.clear();//清空之后,vec.size()为0

2.2. 常见定义方法:

(1) vector<int> a(5); //定义了5个整型元素的向量(<>中为元素类型名,它可以是任何合法的数据类型),但没有给出初值,其值是不确定的.
(2)vector<int> a(5,1);//定义了5个整型元素的向量,且给出每个元素的初值为1
(3)vector<int> a(b); //用b向量来创建a向量,整体复制性赋值
(4)vector<int> a(b.begin(),b.begin+3); //定义了a值为b中第0个到第2个(共3个)元素
(5)int b[7]={1,2,3,4,5,9,8}; vector<int> a(b,b+7); //从数组中获得初值

2.3. 使用方法

2.3.1 创建一维vector:

vector<int>nums;//不指定长度
vector<int>nums(n); // 指定长度为n

添加元素

nums.push_back(1);//直接从数组末端添加
nums[i] = 1;//直接赋值给第i个位置

删除元素

nums.resize(nums.size-i); //直接将数组长度减小,某种方式上删掉了后面i个
nums.pop_back();//删掉最后一个元素

数组遍历

for(int i = 0; i < nums.size(); i++) cout<<nums[i]<<endl;

获得长度

nums.size()

排序(O(nlogn))

sort(nums.begin(),nums.end());

翻转

reverse(nums.begin(), nums.end());

合并两个vector
合并nums1和nums2,并将合并后的数组赋值给nums

vector<int>nums1(m),nums2(n);
vector<int>nums;
nums.resize(m+n);
merge(nums1.begin(), nums1.end(),nums2.begin(),nums2.end(),nums);

2.3.2 定义二维vector

vector<vector<int> > v;

访问二维vector的元素: 如果指定外层和内层向量的大小,就可用operator[]进行读和写;如果只指定外层向量大小,就能用push_back()函数进行写,不能用operator[]进行读和写。

1). 创建m*n的二维vector:

vector<vector <int> >nums(m ,vector<int>(n)); //m*n的二维vector

定义了一个vector容器,元素类型为vector,初始化为包含m个vector对象,每个对象都是一个新创立的vector对象的拷贝,而这个新创立的vector对象被初始化为包含n个0。
vector(n)表示构造一个无名且含n个0的vector对象。

2). 动态创建m*n的二维vector
方法一:

vector<vector <int> > nums;
nums.resize(m);
for(int i=0;i<m;i++) nums[i].resize(n);

方法二:

vector<vector <int> > nums;
nums.resize(m,vector<int>(n));

3).初始化二维数组

vector<vector `<int>` > nums(m ,vector`<int>`(n,0)); //m*n的二维vector,所有元素为0

获得二维数组的行数:nums.size();
获得二维数组的列数:nums[0].size()

4). 数组遍历

int m = nums.size(),n = nums[0].size();
for(int i = 0; i < m; i++){
    for(int j = 0; j < n; j++){
        cout<<nums[i][j]<<endl;
    }
}

三、vector<int>指针形式比较

在使用STL容器(比如map、list、vector等)的时候,是用放一个对象还是放一个对象指针?
即是用vector还是vector<int*>,这里的vector可以换成其他的容器,int可以换成其他基本类型,也可以自定义的数据结构或类。

1). vector不需要动态操作内存,不用担心内存泄露等问题;vector<int*>要注意new和delete成对使用。
2). 当int改变成其他类型或结构或类的时候,用vector<int*>这种方式比较方便,容器里放的内容占用的内存也相对要少一些,指针在用的时候,去申请空间,不用,那就是个占用4个字节的地址。
3). 当需要对变量不断读写操作时,最好得用指针形式,仅仅通过传递指针加快了访问速度。

vector<int>
vector<int> vecTemp;
for (int i=0; i< 10; i++)
{
	vecTemp.push_back(i);	//这种方式不需要动态new内存,当然也不用delete。
}
vector<int*>
vector<int*> vecTemp;
  for (int i=0; i< 10; i++)
  {
      int* nTemp = new int;
      *nTemp = i;
      vecTemp.push_back(nTemp);
  }

vector<int> *a;
当使用这种vector指针时,指针a代表的是:不能通过a[i]访问值,只可能通过a->at(i)访问值。

四.几种常见场景

4.1 vector<int>& nums

1) int &nums:一个整型变量的引用
2) vector nums:nums是一个容器变量,容器名称为vector,容器内存的数据为int型
3) vector &nums:nums为一个引用,引用的内容是vector这个容器内部存放的整型数据

//1) 创建一维vector
vector<int> nums; //不指定长度
vector<int> nums(n); //指定长度 
//2) 添加元素
nums.push_back(1); //直接在末端添加元素1
//3) 删除元素
nums.resize(num.size-i); //删除后面i个元素
nums.pop_back(); //删除最后一个元素 
//4) 获取长度
nums.size();
//5) 判空
nums.empty();

4.2 vector<int> nums

vector<int>& a;
vector<int> a;

说明: 带&表示传入函数的是vector的引用(即物理位置),函数内部对vector改动,vector就会改变;
不带&表示传入的是vector的复制品(开辟了另一块位置),函数内部对其改动,不会影响原本的vector;

4.3 vector< vector<int> > v(m, vector<int>(n) );

定义了一个vector容器,元素类型为vector,初始化为包含m个vector对象,每个对象都是一个新创立的vector对象的拷贝,而这个新创立的vector对象被初始化为包含n个0。
从结果上看,类似于创建了一个m×n的二维数组,而且可以通过v[i][j]的方式来访问元素(vector支持下标访问元素)。

4.4 vector< vector <int> > dp(m, vector<int>(n) )

vector<类型>标识符(最大容量,初始所有值)
vector< vector<int> > v(m, vector<int>(n) );定义了一个vector容器,元素类型为vector,初始化为包含m个vector对象,每个对象都是一个新创立的vector对象的拷贝,而这个新创立的vector对象被初始化为包含n个0。

有关C++中vector<vector<int> >的用法的更多相关文章

  1. ruby - 将数组的内容转换为 int - 2

    我需要读入一个包含数字列表的文件。此代码读取文件并将其放入二维数组中。现在我需要获取数组中所有数字的平均值,但我需要将数组的内容更改为int。有什么想法可以将to_i方法放在哪里吗?ClassTerraindefinitializefile_name@input=IO.readlines(file_name)#readinfile@size=@input[0].to_i@land=[@size]x=1whilex 最佳答案 只需将数组映射为整数:@land边注如果你想得到一条线的平均值,你可以这样做:values=@input[x]

  2. ruby - 在 Ruby 中实现 to_int 和 to_str 的后果 - 2

    我haveaclass它公开了一个字符串值和一个int值(分别是命令输出和退出代码)。除了通过to_s和to_i公开它们之外,我还使用to_str和to_int,如下所示:classStatusdefto_s@outputendalias:to_str:to_sdefto_i@status.exitstatusendalias:to_int:to_iend我的想法是能够在尽可能多的情况下使用这个对象。将其强制转换为字符串或整数会增加可用性。例如,我可以将对象与字符串连接起来:a_string="Outputwas:"+results(我想用这个作为int强制转换的例子,但是Fixnum

  3. ruby - 有人可以解释一下在 Ruby 中注入(inject)的真实、通俗易懂的用法吗? - 2

    我正在学习Ruby,遇到了inject。我正处于理解它的风口浪尖,但当我是那种需要真实世界的例子来学习一些东西的人时。我遇到的最常见的例子是人们使用inject来添加一个(1..10)范围的总和,我不太关心这个。这是一个任意的例子。在实际程序中我会用它做什么?我正在学习,所以我可以继续使用Rails,但我不必有一个以Web为中心的示例。我只需要一些我可以全神贯注的目标。谢谢大家。 最佳答案 inject有时可以通过它的“其他”名称reduce更好地理解。它是一个对Enumerable进行操作(迭代一次)并返回单个值的函数。它有许多有

  4. ruby-on-rails - ruby rails 将参数转换为 int 数组 - 2

    我正在通过get发送数据,我需要将其放入一个int数组中以便在查找中使用。这是我的代码:@found=Array.newparams['candidate'].eachdo|c|@found我的网址是这样的http://localhost:3000/export/candidate?candidate[]=3&candidate[]=4&commit=Export如果它有任何不同,我将它用于此查找@candidate=Candidate.find(:all,:conditions=>["candidates.idIN?",@found])但目前它并没有把它放在一个真正的数组中,因为我得

  5. ruby - 使用法拉第上传文件 - 2

    我在尝试使用Faraday将文件上传到网络服务时遇到问题。我的代码:conn=Faraday.new('http://myapi')do|f|f.request:multipartendpayload={:file=>Faraday::UploadIO.new('...','image/jpeg')}conn.post('/',payload)尝试发布后似乎没有任何反应。当我检查响应时this是我所看到的:#:post,:body=>#,#,@opts={}>,#],@index=0>>,#>],@ios=[#,#,@opts={}>,#],@index=0>,#],@index=0>

  6. ruby - rspec: raise_error 用法来匹配错误信息 - 2

    我使用raise(ConfigurationError.new(msg))引发错误我试着用rspec测试一下:expect{Base.configuration.username}.toraise_error(ConfigurationError,message)但这行不通。我该如何测试呢?目标是匹配message。 最佳答案 您可以使用正则表达式匹配错误消息:it{expect{Foo.bar}.toraise_error(NoMethodError,/private/)}这将检查NoMethodError是否由privateme

  7. 【ChatGPT】ChatGPT 的 N 种用法 - 2

    目录ChatGPT简介技术原理应用未来发展ChatGPT的10 种用法ChatGPT简介ChatGPT是一种基于深度学习的大型语言模型,由OpenAI公司开发。技术原理GPT是GenerativePre-trainedTransformer的缩写,意为生成式预训练变压器。它的技术原理是使用了一个基于注意力机制的变压器(Trans

  8. ruby - 重构 Ruby : Converting string array to int array - 2

    我正在重构一个西洋跳棋程序,我正在尝试将玩家移动请求(例如以“3、3、5、5”的形式)处理到一个int数组中。我有以下方法,但感觉不像我所知道的那样像Ruby:deftranslate_move_request_to_coordinates(move_request)return_array=[]coords_array=move_request.chomp.split(',')coords_array.each_with_indexdo|i,x|return_array[x]=i.to_iendreturn_arrayend我用它进行了以下RSpec测试。it"translatesa

  9. arrays - 在 Ruby 中将字符串转换为 int 数组 - 2

    如何将字符串:s='23534'转换为这样的数组:a=[2,3,5,3,4]有没有一种方法可以遍历ruby​​中的字符并将它们中的每一个转换为to_i或者甚至像Java一样将字符串表示为char数组,然后转换所有字符to_i如您所见,我在字符串中没有这样的分隔符,,我在SO上找到的所有其他答案都包含一个分隔符。 最佳答案 一个简单的衬里是:s.each_char.map(&:to_i)#=>[2,3,5,3,4]如果您希望在字符串不只包含整数时显示错误,您可以这样做:s.each_char.map{|c|Integer(c)}这会引

  10. ruby - 是否有 Rack::Session::Cookie 用法的基本示例? - 2

    我找不到任何使用Rack::Session::Cookie的简单示例,并且希望能够将信息存储在cookie中,并在以后的请求中访问它并让它过期.这些是我能找到的唯一示例:HowdoIset/getsessionvarsinaRackapp?http://rack.rubyforge.org/doc/classes/Rack/Session/Cookie.html这是我得到的:useRack::Session::Cookie,:key=>'rack.session',:domain=>'foo.com',:path=>'/',:expire_after=>2592000,:secret=

随机推荐