so I have a mini assignment and 1 of the question is as such: In a 100-floor building, a lift starts from the 1st floor and along the way, it stops at different floors to pick up people. This are the floors the lift stops at: 1(the start), 5, 14, 29, 80, 99. Find the difference between each floor the lift stops at.
I have to use as many concepts we learn in class as possible in this mini assignment. So I plan to use a vector (as a container to contain the different number of floors), a function (to calculate the difference between each floor) and returning back an array to print the difference.
How do I write a function which takes a vector, perform some calculations (adjacent_difference in my case) and then return an array.
This is how I would've done it if I were to return another vector, but I do not know how to tweak it to make it return an array instead:
#include <iostream>
#include <vector>
#include <numeric>
#include <algorithm>
std::vector<int> calculateDiff (std::vector<int> v);
int main()
{
std::vector<int> vec {1, 5, 14, 29, 80, 99};
for(auto iterator = vec.begin(); iterator != vec.end(); ++iterator)
{
std::cout << "Floors the lift stop at: ";
std::cout << *iterator << std::endl;
}
std::vector<int> diff = calculateDiff(vec);
for(auto iterator = diff.begin(); iterator != diff.end(); ++iterator)
{
std::cout << "Floor Difference: ";
std::cout << *iterator << std::endl;
}
}
std::vector<int> calculateDiff (std::vector<int> v)
{
std::vector <int> floorDiff;
floorDiff.resize(v.size());
std::adjacent_difference(v.begin(), v.end(), floorDiff.begin());
floorDiff.erase(floorDiff.begin()); //First element does not give the difference
return floorDiff;
}
Using a std::vector
as the return type is the best strategy, IMO. However, you'll have to tweak your function a little bit. You have to make sure that floorDiff
is as large as v
.
std::vector <int> floorDiff(v.size());
That is necessary since std::adjacent_difference
does not allocate memory.
If you must return an array for whatever reason, you can simply expand your function a bit.
// Pass the input by const& to avoid the cost of a copy
// and to indicate that it won't be modified in the function.
int* calculateDiff (std::vector<int> const& v)
{
std::vector <int> floorDiff(v.size());
floorDiff.resize(v.size());
std::adjacent_difference(v.begin(), v.end(), floorDiff.begin());
int* arr = new int[floorDiff.size()-1];
std::copy(floorDiff.begin()+1, floorDiff.end(), arr);
return arr;
}
Make sure to deallocate the memory in the calling function.
If you feel a need to use both an array and a vector, it's "more C++" to do it the other way around - passing an "array" (ie a pointer and a size) and returning a vector.
You also get to do some pointer arithmetic and illustrate the generality of <algorithm>
in calculateDiff
.
std::vector<int> calculateDiff (const int* v, size_t size)
{
std::vector<int> floorDiff{size};
std::adjacent_difference(v, v + size, floorDiff.begin());
floorDiff.erase(floorDiff.begin())
return floorDiff;
}
Using std::vector
throughout is the correct choice, but there are some style issues that you can improve
int main()
{
// vec is undescriptive of what it represents
std::vector<int> floors {1, 5, 14, 29, 80, 99};
for(auto iterator = floors.begin(); iterator != floors.end(); ++iterator)
{
// << can be chained
std::cout << "Floors the lift stop at: " << *iterator << std::endl;
}
// Note that you repeat the "Floors the lift stop at: "
// If you only want one line, you can instead:
/*
std::cout << std::cout << "Floors the lift stop at: ";
std::copy(floors.begin(), floors.end(), std::ostream_iterator<int>(std::cout, " "));
std::cout << std::endl;
*/
std::vector<int> diffs = calculateDiffs(vec);
for(auto iterator = diffs.begin(); iterator != diffs.end(); ++iterator)
{
std::cout << "Floor Difference: " << *iterator << std::endl;
}
// and again, can std::copy into a std::ostream_iterator
}
std::vector<int> calculateDiffs (std::vector<int> values)
{
// values is already a copy, as you passed by value
std::adjacent_difference(values.begin(), values.end(), values.begin());
values.erase(values.begin()); //First element does not give the difference
return values;
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.