ฉันจะแปลง a std::vector<double>
เป็น a ได้double array[]
อย่างไร
ฉันจะแปลง a std::vector<double>
เป็น a ได้double array[]
อย่างไร
คำตอบ:
มีเคล็ดลับที่ค่อนข้างง่ายในการทำเช่นนี้เนื่องจาก spec ในขณะนี้รับประกันเวกเตอร์จัดเก็บองค์ประกอบของพวกเขาอย่างต่อเนื่อง:
std::vector<double> v;
double* a = &v[0];
double*
จุดที่ชี้ไปยังข้อมูลเดียวกัน คำตอบนี้ใช้ได้กับกรณีนั้น
std::vector<double> v; double* a = v.data();
เพื่ออะไร? คุณต้องชี้แจง: คุณต้องการตัวชี้ไปยังองค์ประกอบแรกของอาร์เรย์หรืออาร์เรย์หรือไม่?
หากคุณกำลังเรียกฟังก์ชัน API ที่คาดว่าอดีตคุณสามารถทำอะไรdo_something(&v[0], v.size())
ที่v
เป็นเวกเตอร์ของdouble
s องค์ประกอบของเวกเตอร์นั้นต่อเนื่องกัน
มิฉะนั้นคุณต้องคัดลอกแต่ละองค์ประกอบ:
double arr[100];
std::copy(v.begin(), v.end(), arr);
ตรวจสอบให้แน่ใจว่าไม่เพียง แต่arr
มีขนาดใหญ่พอ แต่ที่arr
จะเติมให้เต็มหรือคุณมีค่าเริ่มต้น
size()
ฟังก์ชันของstd:vector
คุณจะต้องใช้new
หรือmalloc
ทำเช่นนั้น ตามที่ได้อธิบายไว้แล้ว (โดยคุณ) ว่าdouble arr[v.size()]
ไม่ถูกต้อง การใช้เวกเตอร์แทนสิ่งใหม่เป็นความคิดที่ดี แต่ประเด็นทั้งหมดของคำถามคือวิธีที่คุณสามารถแปลงเวกเตอร์เป็นอาร์เรย์
vector<double> thevector;
//...
double *thearray = &thevector[0];
สิ่งนี้รับประกันว่าจะทำงานได้ตามมาตรฐานอย่างไรก็ตามมีข้อแม้บางประการ: โดยเฉพาะอย่างยิ่งให้ใช้เฉพาะthearray
เมื่อthevector
อยู่ในขอบเขตเท่านั้น
empty()
อย่างอื่นสิ่งนี้จะก่อให้เกิด UB ที่น่ากลัว
เวกเตอร์อย่างมีประสิทธิภาพคืออาร์เรย์ใต้ผิวหนัง หากคุณมีฟังก์ชั่น:
void f( double a[]);
คุณสามารถเรียกมันว่าแบบนี้:
vector <double> v;
v.push_back( 1.23 )
f( &v[0] );
คุณไม่จำเป็นต้องแปลงเวกเตอร์เป็นอินสแตนซ์อาร์เรย์จริง
f( &v[0] );
บรรทัดสุดท้ายของคุณ
ตามที่ std::vector<int> vec
vec ที่จะได้รับint*
คุณสามารถใช้สองวิธี:
int * arr = & vec [0];
int * arr = vec.data ();
หากคุณต้องการแปลงT
เวคเตอร์ประเภทใด ๆให้T* array
เปลี่ยนข้างบนint
T
ไป
ฉันจะแสดงให้คุณเห็นว่าทำไมผลงานทั้งสองข้างต้นเพื่อความเข้าใจที่ดี
std::vector
เป็นอาร์เรย์แบบไดนามิกเป็นหลัก
สมาชิกข้อมูลหลักดังนี้:
template <class T, class Alloc = allocator<T>>
class vector{
public:
typedef T value_type;
typedef T* iterator;
typedef T* pointer;
//.......
private:
pointer start_;
pointer finish_;
pointer end_of_storage_;
public:
vector():start_(0), finish_(0), end_of_storage_(0){}
//......
}
range (start_, end_of_storage_)
เป็นหน่วยความจำทั้งหมดอาร์เรย์เวกเตอร์จัดสรร;
range(start_, finish_)
เป็นหน่วยความจำทั้งหมดอาร์เรย์เวกเตอร์ที่ใช้;
range(finish_, end_of_storage_)
คือหน่วยความจำอาร์เรย์สำรอง
ตัวอย่างเช่นเป็น vec เวกเตอร์ ซึ่งมี {9, 9, 1, 2, 3, 4} ตัวชี้อาจต้องการด้านล่าง
ดังนั้น&vec[0]
= start_ (address.) (start_ เทียบเท่ากับ int * array head)
ในฟังก์ชันสมาชิกเพียงแค่กลับ start_c++11
data()
pointer data()
{
return start_; //(equivalent to `value_type*`, array head)
}
เราสามารถทำได้โดยใช้วิธี data () C ++ 11 ให้วิธีการนี้
#include<bits/stdc++.h>
using namespace std;
int main()
{
ios::sync_with_stdio(false);
vector<int>v = {7, 8, 9, 10, 11};
int *arr = v.data();
for(int i=0; i<v.size(); i++)
{
cout<<arr[i]<<" ";
}
return 0;
}
std::vector<double> vec;
double* arr = vec.data();
foo(&array[0], array.size());
ถ้าคุณมีฟังก์ชั่นแล้วคุณอาจจะต้องนี้: หากคุณจัดการกับสถานการณ์ที่คุณต้องการอาเรย์แล้วคุณจะต้องปรับโครงสร้างเวกเตอร์นั้นเป็นอาร์เรย์แบบขยายโดยทั่วไปคุณควรใช้มัน
คุณสามารถทำอะไรเช่นนี้
vector <int> id;
vector <double> v;
if(id.size() > 0)
{
for(int i = 0; i < id.size(); i++)
{
for(int j = 0; j < id.size(); j++)
{
double x = v[i][j];
cout << x << endl;
}
}
}