Thread: Iterating over an array of C++ in a for loop

  1. #1
    Registered User FortranLevelC++'s Avatar
    Join Date
    May 2013
    Location
    United States
    Posts
    81

    Iterating over an array of C++FUNCTIONS in a for loop

    Thank you for your precious time.

    With my limited understanding of C++, it seems that instead of directly defining an array of C++ functions, we need an array of pointers to functions.

    This is the only way I know how to use a for loop in C++ to iterate over a family of functions. I am creating a map from the names of functions to functions as follows:

    Code:
    map<string,void (*)(string, vector<string> &, vector<vector<RAStruct > > &  ) >map_FuncNamesToFuncs;

    And once this map above is prepared and populated, finally I am able to iterate over the functionswith a for loop like this:
    Code:
    
          vector<string>::iterator end = vec_NamesOfAverageFunctions.end() ;
          for(vector<string>::iterator itr=vec_NamesOfAverageFunctions.begin() ; itr != end; ++itr) {
             // map_FuncNamesToFuncs[ (*itr) ](  vec_NamesOfKeyFilesForRandAcc[i] , vec_CoreSymbolInfo, vec_NamesOfSymbolFilesForMarkets[i] )  ;
             map_FuncNamesToFuncs[ (*itr) ](   vec_NamesOfSymbolFilesForMarkets[i], vec_MarketSymbolList, vec_AllSymRecs   )  ;
             cout << "Executed avg function " << *itr  << endl;
    
    
          }


    This works, but if there is a better way to access a family of functions, please let me know.
    In this case, the names of the functions that will be called can be written in a text file and the program that reads the text file can actually enable the map accordingly.

    Thanks!!

    Last edited by FortranLevelC++; 11-26-2018 at 09:18 PM. Reason: Title was not clear

  2. #2
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    I would reach for a typedef, e.g.,
    Code:
    typedef void (*AverageFunction)(std::string, std::vector<std::string>&, std::vector<std::vector<RAStruct>>&);
    Now you can write:
    Code:
    map<string, AverageFunction> map_FuncNamesToFuncs;
    // ...
    
    for (const auto& functionName : vec_NamesOfAverageFunctions) {
        map_FuncNamesToFuncs[functionName](vec_NamesOfSymbolFilesForMarkets[i], vec_MarketSymbolList, vec_AllSymRecs);
        cout << "Executed avg function " << functionName << endl;
    }
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  3. #3
    Registered User FortranLevelC++'s Avatar
    Join Date
    May 2013
    Location
    United States
    Posts
    81
    This is wonderful because it not only simplifies many things, but also prevents potential errors!!!

    From now on I will use this, but I first need to mentally get used to switching from ''*itr' to '&functionName' syntax.

    However, your comment leads me to ask you the following question: does C++ absolutely guarantee that when we use such a range-based for loop, the elements of the array or map of functions will be accessed/called in the same order as the original array/map was defined?

    Some languages might access the elements in the for loop in a random or in some way unpredictably changeable way .

    When we are using an iterator in a for loop, at least we know that it is being incremented like in the traditional for loops.

  4. #4
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Quote Originally Posted by FortranLevelC++
    does C++ absolutely guarantee that when we use such a range-based for loop, the elements of the array or map of functions will be accessed/called in the same order as the original array/map was defined?
    No, it will be accessed as if you looped over the container with a forward iterator. This does not necessarily correspond with how you populated the container, e.g., a std::set likely uses a balanced binary tree internal representation, so when accessing it with a forward iterator you likely will get the elements in sorted order unrelated to insertion order, and then a std::unordered_set is likely to be, well, unordered due to the hash table representation, yet also unrelated to insertion order.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  5. #5
    Registered User FortranLevelC++'s Avatar
    Join Date
    May 2013
    Location
    United States
    Posts
    81
    Quote Originally Posted by laserlight View Post
    No, it will be accessed as if you looped over the container with a forward iterator. This does not necessarily correspond with how you populated the container, e.g., a std::set likely uses a balanced binary tree internal representation, so when accessing it with a forward iterator you likely will get the elements in sorted order unrelated to insertion order, and then a std::unordered_set is likely to be, well, unordered due to the hash table representation, yet also unrelated to insertion order.
    Of course, in the case of an unordered std::set, there would not be any consistent order in which the for loop accesses the elements.
    But at least in my program where there is only a map of functions, when these functions are executed in the for loop that uses iterators,
    it seems that the execution order is the same as the order in which the map of functions was populated. Maybe I was just lucky.
    I will have to double check this because some functions depend on the result of the previous function call.

    Anyway, I am very pleased with the rate at which C++ is being upgraded: maybe in a few years C++
    will become more like Scala, at least for composing functions and building arrays of functions.
    Last edited by FortranLevelC++; 11-26-2018 at 10:28 PM.

  6. #6
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Quote Originally Posted by FortranLevelC++
    it seems that the execution order is the same as the order in which the map of functions was populated. Maybe I was just lucky.
    I will have to double check this because some functions depend on the result of the previous function call.
    I don't see how that matters: you populate the map, and then later you access its elements by function name to make the function calls. Hence, the order in which the map is populated should not matter. What matters is the order in which you use the function names to access the map so as to call the functions, and this is determined by the vector of names.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  7. #7
    Registered User FortranLevelC++'s Avatar
    Join Date
    May 2013
    Location
    United States
    Posts
    81
    Of course, what you said is what I meant. The order in which the function names in the vector of names is what the iteration is over, by means of the map.

    Again, thanks for your precious time. As you said in the other thread, keeping the function names in a text file as parameters can make it difficult to modify the program.
    I need to do more research, but at least the calculations are OK.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. While Loop not iterating
    By csmith03 in forum C Programming
    Replies: 6
    Last Post: 10-16-2017, 01:31 PM
  2. Replies: 5
    Last Post: 02-20-2014, 06:26 PM
  3. Iterating through a multidimensional array
    By Angus in forum C Programming
    Replies: 20
    Last Post: 06-05-2009, 09:32 AM
  4. Iterating through a map that contains a vector
    By AngryStyro in forum C++ Programming
    Replies: 2
    Last Post: 06-08-2008, 05:01 AM
  5. Iterating through an array
    By MikeyIckey in forum C Programming
    Replies: 15
    Last Post: 11-10-2007, 10:26 PM

Tags for this Thread