Template Function to reciveve an array of elements

I need to know how to write a template function that will recieve an array of elements of type K, of any size, add up the elements using the + operator, and return the sum to the calling function (only has to handle arrays).  This function should be usable for any data type K for which the operator + is defined.
waylonwhalesAsked:
Who is Participating?
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

CayceCommented:
This really looks like homework to me.

Basically you can create a template to a vector of any type the perform the sum of each member.

Your declaration would be something like this:

template<class T>
void Sum(T& result, std::vector<T> array);

you could also use:

templace<class T>
T Sum(std::vector<T> array);

In the first case the caller is reponsible for sending a T value of 0 (whatever zero is for T type), on the second case, you MUST assign the result to the first element of the array, then add the rest of them.

Now just implement the sum using an iterator. If the type T doesn't support the + operator the compiler will issue an error.
0
waylonwhalesAuthor Commented:
yes this is a project
the purpose of Writing this template function is to use it to simplify an application program to read a sequence of values of a specific type into an appropriate array(which comes from a simple text file), call the template function to obtain the sum, and print the result.

template<class T>
T Sum (TList[ ], ....)
{
     for (i = 0, i < TList[ ], i++) //traverse through the array
       if (list != null)
       {
            //add up the elements and return a sum??  list[?] = a+b+c+.....
       }
       else
       {
         cout << "....... ...." << endl;
      }

int main ()
{
  a_file.open("words.txt");
 .
 .
 .
}
questions...
the array is of unknown size...but is limited, and of unknown type...but the
template function handles the type differences
how do you code an addition of an unknown amount of elements
do you use the traversal...
int j = Tlist[i].size()
cout <<  j << endl;  ??
I just need some insight to fill in my missing code to get this thing to work
thanks again for your time
0
CayceCommented:
You'll be better using the STL vector instead of your own list. Those have a size() property.

The thing is, that the procedure you're asking for results so simple that giving you more help would be doing it for you :)

#include <vector>

template<class T>
T Sum(std::vector<T>& array)
{
  T result;
  if(array.size() > 0)
  {
    result = array[0];
    for(unsigned int i = 1; i < array.size(); i++)
      result = result + array[i];
  }
  return result;
}

Note, that the above code will require the next thing from the T type:

1) T must support the + operator

2) T must have a default constructor, if it doesn't you should make another procedure like this:

T& Sum(T& result, std::vector<T>& array)
{
  if(array.size() > 0)
  {
    result = array[0];
    for(unsigned int i = 1; i < array.size(); i++)
      result = result + array[i];
  }
  return result;
}

Why? Because on the previous version of the procedure there was this line:
T result;
T could be as simple as a char, but it also could be a very complicated class which requires a lot of memory and doesn't have a default constructor (with no parameters).

3) T should have the assignment operator overloaded.

That means a class should be like this to work fine with your Sum()
// a basic example
class C
{
private:
  float val;
public:
 C()
 {
  val = 0;
 }
 C(const C& c)
 {
  *this = c;
 }
 C& operator=(const C& c)
 {
  val = c.val;
  return *this;
 }
 friend C operator + (C& c1, C& c2):
};

C operator + (C& c1, C& c2)
{
  C c3;
  c3.val = c1.val + c2.val;
  return c3;
}
0
Cloud Class® Course: Python 3 Fundamentals

This course will teach participants about installing and configuring Python, syntax, importing, statements, types, strings, booleans, files, lists, tuples, comprehensions, functions, and classes.

waylonwhalesAuthor Commented:
my simple template program is almost complete...except I'm getting a error that i'm not sure how to fix.  Here is the complete code:


using namespace std;

template<class T>
T Sum(std::vector<T>& array, int amount)
{
  T result;
  if(amount > 0)
  {
    result = array[0];
    for(unsigned int i = 1; i < amount; i++)
      result = result + array[i];
  }
  return result;
}

int main()
{
   
      int element_position = 0;
      const int elements_capacity = 100;
      int elements[elements_capacity];
      
      string line1;
      int answer1;
      ifstream a_file;
      a_file.open("template_test.txt");
      if (a_file.fail())
         {
            cout << "Error opening" << "template_test.txt" << "\n";
            return 1;
         }

      //for every int successfully read
        while ( element_position < elements_capacity
                  && (a_file >> elements[element_position]) )
        {
             
             element_position++;
             
        }

     
        answer1 =  Sum (elements, element_position);
      cout << answer1 << endl;
      a_file.close();

//here is the error message....

Compiling...
Tfunction.cpp
c:\program files\microsoft visual studio\myprojects\lab6\tfunction.cpp(64) : error C2784: 'T __cdecl Sum(class std::vector<T,class std::allocator<T> > &,int)' : could not deduce template argument for 'class std::vector<_Ty,class std::allocator<_Ty>
> &' from 'int [100]'
Error executing cl.exe.

Tfunction.obj - 1 error(s), 0 warning(s)

//if I could get this error fixed...I think the program will work!  Thanks for the
expertise!!
0
CayceCommented:
You need to specifiy the type on the call to sum:

Like this

 answer1 =  Sum<int>(elements, element_position);
0
CayceCommented:
BTW: you are not really using STL vectors, so change Sum declaration to:

template<class T>
T Sum(T array[], int amount)
0
waylonwhalesAuthor Commented:
yes the first part of the project works...! thank you!
but I still have one more question.....
the code calls the (integers) from a line of text in a file called variable a_file
this file has two more lines of text of different type. It looks like this:

37 -500 99 1024 365 5 8 101 -77 280 311 260 445
1.2 2.345 3.57999 -273.48967 0.0 55.66 -3.545
Alph beti zing Is No Job For A Hig hl y Pa id Prog ramm er!

The program makes use of the template and adds up the integers from line 1 nicely.
I want the program to go to the next line and use the template to add them as well.
Now since these two lines are of different type, I must specify a new array of type double correct?  As well as rename my variables to accept type double...I also closed the file and reopened it...(b_file) which I didn't want to do.  How do I get the program to look to line 2 for the type double? I thought it would be as simple as adding a very similar block of code.  (And finally line 3 for type string)? Here is the code with errors:

using namespace std;

template<class T>
T Sum(T array[], int amount)

{
  T result;
  if(amount > 0)
  {
    result = array[0];
    for(unsigned int i = 1; i < amount; i++)
      result = result + array[i];
  }
  return result;
}

int main()
{
   
      int element_position = 0;
      const int elements_capacity = 100;
      int elements[elements_capacity];
      
      
      int answer1;
      ifstream a_file;
      
      a_file.open("template_test.txt");
      
      if (a_file.fail())
         {
            cout << "Error opening" << " template_test.txt" << "\n";
            return 1;
         }

      //for every int successfully read
        while ( element_position < elements_capacity
                  && (a_file >> elements[element_position]) )
        {
             
             element_position++;
             
        }

     
        answer1 =  Sum(elements, element_position);
      cout << answer1 << endl;
      a_file.close();
   //*******************************************************

      
      double new_element_position = 0;
      const double new_elements_capacity = 100;
      double new_elements[elements_capacity];

      double answer2;

      ifstream b_file;
      
      b_file.open("template_test.txt");
      
      if (b_file.fail())
         {
            cout << "Error opening" << " template_test.txt" << "\n";
            return 1;
         }
      
      
      //for every double successfully read
        while ( new_element_position < new_elements_capacity
                  && (b_file >> new_elements[new_element_position]) )
        {
             
             new_element_position++;
             
        }

     
        answer2 =  Sum(new_elements, new_element_position);
      cout << answer2 << endl;

         b_file.close();

        
}

Tfunction.cpp
C:\Program Files\Microsoft Visual Studio\MyProjects\Lab6\Tfunction.cpp(92) : error C2108: subscript is not of integral type
C:\Program Files\Microsoft Visual Studio\MyProjects\Lab6\Tfunction.cpp(92) : error C2679: binary '>>' : no operator defined which takes a right-hand operand of type 'double *' (or there is no acceptable conversion)
C:\Program Files\Microsoft Visual Studio\MyProjects\Lab6\Tfunction.cpp(92) : fatal error C1903: unable to recover from previous error(s); stopping compilation
Error executing cl.exe.

Tfunction.obj - 3 error(s), 0 warning(s)  

0
CayceCommented:
looks like you should be reading line by line, then using a text stream to parse the lines into ints, then doubles, then strings.

Your loop where you read from the file is incorrect.

Another recommendation would be to use vector instead of arrays.
0
waylonwhalesAuthor Commented:
A vector would be much better...because it is more dynamic...but unfortunately I cannot use a vector (according to the rules).  I can't seem to find an example of how to continue the reading of my text file to incorporate the next line of text.  What I do know is that once the >> extraction reaches the newline ch. at the end of the first line of text it reaches a fail state and terminates the read.  The type difference here in the text file is really causing problems especially with the limited use of the array.  I would like to know if there is a way to create a loop with a counter and a test to handle the different types in one shot?
0
CayceCommented:
Use a strstream for each line. Something like this:

#include <strstream>
#include <fstream>
foo()
{
  fstream f;
  f.open("myfile.txt");
  char buffer[1024] = {0};

  f.getline(buffer, 1024);
  strstream ss_int(buffer, 1024);
  //
  // Read ints from ss_int;
  //
  f.getline(buffer, 1024);
  strstream ss_double(buffer, 1024);
  //
  //  Read doubles from ss_double
  //
  f.close();
}
0
waylonwhalesAuthor Commented:
wow, that worked...I have three different outputs for the three different types...although I'm sure that it isn't entirely correct output.  The syntax produces no errors but the logic still isn't right.  (And I still can't rename my variable to reflect the type I'm dealing with...it always wants ints)  I"ll show the complete coding below with output:

using namespace std;

template<class T>
T Sum(T array[], int amount)

{
  T result;
  if(amount > 0)
  {
    result = array[0];
    for(unsigned int i = 1; i < amount; i++)
      result = result + array[i];
  }
  return result;
}

int main()
{
   
      int element_position = 0;
      const int elements_capacity = 100;
      int elements[elements_capacity];
      int new_element_position = 0;
      const int new_elements_capacity = 100;
      int new_elements[new_elements_capacity];
      int new2_element_position = 0;
      const int new2_elements_capacity = 100;
      int new2_elements[new2_elements_capacity];
      
      int answer1;
      double answer2;
      string answer3;
      fstream a_file;
      char buffer[1024] = {0};
      
      a_file.open("template_test.txt");
      
      if (a_file.fail())
         {
            cout << "Error opening" << " template_test.txt" << "\n";
            return 1;
         }

     a_file.getline(buffer, 1024);
     strstream ss_int(buffer, 1024);
  //
  // Read ints from ss_int;
  //
 
      
        while ( element_position < elements_capacity
                  && (ss_int >> elements[element_position]) )
        {
             
             element_position++;
             
        }

     
        answer1 =  Sum(elements, element_position);
      cout << answer1 << endl;
     
   //*******************************************************
 
        
        
        a_file.getline(buffer, 1024);
        strstream ss_double(buffer, 1024);
      //
      //  Read doubles from ss_double
      //
 
 
  while ( new_element_position < new_elements_capacity
                  && (ss_int >> new_elements[new_element_position]) )
        {
             
             new_element_position++;
             
        }

      answer2 =  Sum(new_elements, new_element_position);
      cout << "\n" << answer2 << endl;


 //**********************************************************


        a_file.getline(buffer, 1024);
        strstream ss_string(buffer, 1024);
      //
      //  Read string from ss_string
      //
 
 
  while ( new2_element_position < new2_elements_capacity
                  && (ss_int >> new2_elements[new2_element_position]) )
        {
             
             new2_element_position++;
             
        }

      answer3 =  Sum(new2_elements, new2_element_position);
      cout << "\n" << answer3 << endl;
 
        
        a_file.close();       
}

output:
2358
-8.58993e +008
|}

 text file:
37 -500 99 1024 365 5 8 101 -77 280 311 260 445
1.2 2.345 3.57999 -273.48967 0.0 55.66 -3.545
Alph beti zing Is No Job For A Hig hl y Pa id Prog ramm er!
 
0
CayceCommented:
Shouldn't your arrays be:

     int int_element_position = 0;
     const int int_elements_capacity = 100;
     int int_elements[elements_capacity];
     int double_element_position = 0;
     const int double_elements_capacity = 100;
     double double_elements[double_elements_capacity];
     int string_element_position = 0;
     const int string_elements_capacity = 100;
     string string_elements[string_elements_capacity];

And call Sum like this:

  int int_answer = Sum<int>(int_elements, int_element_position);
// ...
  double double_answer = Sum<double>(double_elements, double_element_position);
// ...
  string string_answer = Sum<string>(string_elements, string_element_position);

0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
Editors IDEs

From novice to tech pro — start learning today.

Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.