简体   繁体   English

如何从C++中的函数返回数组

[英]How to return an array from a function in c++

Hello I am attempting to get data from an input file and have that placed in an array.您好,我正在尝试从输入文件中获取数据并将其放入数组中。 I was able to complete my one function and have the array return as shown below:我能够完成我的一个函数并返回数组,如下所示:

string * animal_name_grab() 
{
        static string animal_name[SIZE];
        int cntr = 0;
        static string line_skip[SIZE];
    while (!input_animals.eof())
    {
        getline(input_animals, animal_name[cntr]);
        getline(input_animals, line_skip[cntr]);
        cntr++;
    }
    return (animal_name);
}

Now I am attempting to do the same thing, but add up the sum of the digits.现在我正在尝试做同样的事情,但将数字的总和相加。 Which I don't see exactly what is wrong with it.我不明白它到底有什么问题。 I did my function call the exact same way I did the previous one, but I am inserting it too just in case.我的函数调用方式与上一个完全相同,但为了以防万一,我也插入了它。 Declared double *array_animal_total;声明 double *array_animal_total; Function call - array_animal_total = animal_total_grab();函数调用 - array_animal_total = animal_total_grab();

double * animal_total_grab()
{
        static double animal_total[SIZE];
        static string line_skip[SIZE];
        int cntr = 0;
        double sum = 0;
        double total_count;
    while (!input_animals.eof())
    {
        getline(input_animals, line_skip[cntr]);

            for ( int i ; i < 10 ; i++)
            {
            input_animals >> total_count;
            sum = sum + total_count;    
            }
        animal_total[cntr] = sum;

        cntr++;
    }
    return (animal_total);
}

Please advise me if this is too much code to enter on here so I can edit it.如果代码过多,无法在此处输入,请告知我,以便我可以对其进行编辑。 I just wanted it to be proven that I understand the material, I just am having a bit of trouble.我只是想让它证明我理解材料,我只是遇到了一些麻烦。 I am a beginner, so please be nice.我是初学者,所以请善待。

I was able to complete my one function and have the array return as shown below:我能够完成我的一个函数并返回数组,如下所示:

 string * animal_name_grab()

You aren't returning an array.你没有返回一个数组。 You are returning a pointer.您正在返回一个指针。 The pointer points to an element of an array.指针指向数组的一个元素。

How to return an array from a function in c++如何从C++中的函数返回数组

It is in fact impossible to directly return an array from a function in C++.事实上,在 C++ 中直接从函数返回一个数组是不可能的。 However, it is possible to return an instance of a class, and classes can have array members, so if you wrap the array inside a class, then you can return that wrapper object.但是,可以返回类的实例,并且类可以具有数组成员,因此如果将数组包装在类中,则可以返回该包装对象。 There is a standard template for such array wrapper class.这种数组包装类有一个标准模板。 Its name is std::array .它的名字是std::array Example:例子:

std::array<std::string, SIZE> animal_name_grab()
{
    std::array<std::string, SIZE> animal_name;
    ...
    return animal_name;
}

Note that copying large arrays is potentially slow, and you'd be relying on compiler optimisation to avoid copying the return value.请注意,复制大型数组可能会很慢,并且您将依赖编译器优化来避免复制返回值。 It is sometimes more efficient, and often more flexible to use an output iterator instead of returning an array.有时使用输出迭代器而不是返回数组更有效,而且通常更灵活。

You asked for suggestions, so there you are: If you want to make your code more C++-like and modern, consider using a std::array or std::vector instead of a raw array.你征求了建议,所以你得到了:如果你想让你的代码更像 C++ 和现代,考虑使用std::arraystd::vector而不是原始数组。 This allows you to use STL_functions like:这允许您使用 STL_functions,如:

std::for_each(vector.begin(), vector.end(), [&] (int n) {
sum_of_elems += n;
});

To get the sum of the elements.得到元素的总和。 You can return vectors but i would recommend you to first create the vector and then pass it by reference.您可以返回向量,但我建议您首先创建向量,然后通过引用传递它。

std::vector<std::string> input;
input.reserve(approxSpace); // Not necessary
getInput(&input); // Fill vector in external function

Also avoid using "magic numbers" like 10 in you case.在这种情况下,还要避免使用“幻数”,例如10 If your projects get bigger it makes it way harder to change things without breaking the code.如果您的项目变得更大,那么在不破坏代码的情况下进行更改会变得更加困难。

You could break it down and define your own types for animal and an animal_collection and add some functions to use them like you wish.您可以将其分解并为animalanimal animal_collection定义您自己的类型,并添加一些函数以按照您的意愿使用它们。 You obviously want to read an animal from a stream so let's create a function for that.您显然想从流中读取animal ,因此让我们为此创建一个函数。 You also want to read a whole collection of animal s so let's add a function for that.您还想阅读整个animal集合,因此让我们为此添加一个函数。

Walkthrough:演练:

#include <iostream>
#include <vector>  // std::vector - a dynamically growing container
                   //               that you can store objects in
#include <sstream> // std::istringstream for demo purposes

// A type to store the characteristics of an animal in. Let's start with a name.
struct animal {
    std::string name;
};

// A function to read one "animal" from std::cin or some other istream.
//
// It's functions like these that makes "cin >> variable;" work in your everyday program.
std::istream& operator>>(std::istream& is, animal& a) {
    std::getline(is, a.name);
    return is;
}

// A function to write one "animal" to std::cout or some other ostream.
std::ostream& operator<<(std::ostream& os, const animal& a) {
    return os << a.name;
}

// A collection of animals.
struct animal_collection {
    // std::vector - This std::vector stores objects of the type "animal".
    //               It has a lot of good features and is often prefered as a container
    //               when the exact number of elements to store is unknown.
    std::vector<animal> creatures;

    // return the number of "animal" objects there are in this "animal_collection"
    size_t size() const { return creatures.size(); }

    // iterator support functions so that you can loop over an animal_collection.
    // In this case, they are mearly proxy functions for the functions in std::vector
    // that we need exposed.

    // const iterators
    auto cbegin() const { return creatures.cbegin(); }
    auto cend() const { return creatures.cend(); }

    auto begin() const { return cbegin(); }
    auto end() const { return cend(); }

    // non-const iterators
    auto begin() { return creatures.begin(); }
    auto end() { return creatures.end(); }
};

// A function to read one "animal_collection" from std::cin or some other istream,
// like a file / ifstream.
std::istream& operator>>(std::istream& is, animal_collection& ac) {
    animal tmp;
    while(is >> tmp) { // use operator>> for "animal"
        // push_back() is a function in std::vector. Since this vector stores "animal"
        // objects and "tmp" is an "animal" object, this works:
        ac.creatures.push_back(tmp);
    }
    return is;
}

// A function to write one "animal_collection" to std::cout or some other ostream,
// like a file / ifstream.
std::ostream& operator<<(std::ostream& os, const animal_collection& ac) {
    // use the iterator support functions added to the "animal_collection" type
    // and loop over all the animal objects inside
    for(const animal& a : ac) {
        os << a << '\n'; // use operator<< that was added for "animal"
    }
    return os;
}

// using the two types created above
int main() {
    std::istringstream cin(
        "Tiger\n"
        "Lion\n"
        "Zebra\n"
        "Dalek\n");

    animal_collection ac;

    // read all "animal" objects into the "animal_collection"
    //
    // emulating reading animals from cin - replace with any istream,
    // like an open file

    cin >> ac; // use operator>> defined for "animal_collection"

    // use the size() function in the "animal_collection":
    std::cout << "there are " << ac.size() << " animal(s):\n";

    // output the whole "animal_collection"
    std::cout << ac;
}

When you need to add characteristics to animal you will only need to change what's relevant for that type.当您需要为animal添加特征时,您只需更改与该类型相关的内容。 The animal_collection will not need changes. animal_collection不需要更改。 The std::vector<animal> inside the animal_collection has a lot of other nice functions that you can also expose via proxy functions just as size() and the begin() / end() family of functions. animal_collectionstd::vector<animal>许多其他不错的函数,您也可以通过代理函数公开​​它们,就像size()begin() / end()系列函数一样。

If you don't want to use anything from the std library you can always just declare the array on the heap so it wont get destructed when you return.如果你不想使用 std 库中的任何东西,你总是可以在堆上声明数组,这样当你返回时它就不会被破坏。

For example:例如:

double * func(){
   double * someArray = new double[3]; //declaring 'someArray' on the heap

   for(int i = 0; i < 3; i++)   //Filling the array with data
      someArray[i] = i;         //filling the array with data

   return someArray;            //since 'someArray' is on the heap it wont be destructed when you return
}

Although don't forget to delete the array after you are done with it.尽管完成后不要忘记删除数组。

Hope this helps.希望这可以帮助。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM