Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. General Programming
  3. C / C++ / MFC
  4. vector of doubles (division)

vector of doubles (division)

Scheduled Pinned Locked Moved C / C++ / MFC
databasegraphicsquestion
22 Posts 5 Posters 0 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • B Offline
    B Offline
    b rad311
    wrote on last edited by
    #1

    Hi, How would I take my vector of doubles and divide each element in the vector by a scalar (without using a for loop and explicitly referring to each element using the loop index)? I tried vec/scalar but that doesn't work.

    L CPalliniC A S 4 Replies Last reply
    0
    • B b rad311

      Hi, How would I take my vector of doubles and divide each element in the vector by a scalar (without using a for loop and explicitly referring to each element using the loop index)? I tried vec/scalar but that doesn't work.

      L Offline
      L Offline
      loyal ginger
      wrote on last edited by
      #2

      You can use a while loop and use an iterator to achieve this.

      B 1 Reply Last reply
      0
      • B b rad311

        Hi, How would I take my vector of doubles and divide each element in the vector by a scalar (without using a for loop and explicitly referring to each element using the loop index)? I tried vec/scalar but that doesn't work.

        CPalliniC Offline
        CPalliniC Offline
        CPallini
        wrote on last edited by
        #3

        With "Mystical-Powers". There's a reason there are iterators in STL containers: you have to iterate. :)

        If the Lord God Almighty had consulted me before embarking upon the Creation, I would have recommended something simpler. -- Alfonso the Wise, 13th Century King of Castile.
        This is going on my arrogant assumptions. You may have a superb reason why I'm completely wrong. -- Iain Clarke
        [My articles]

        In testa che avete, signor di Ceprano?

        1 Reply Last reply
        0
        • L loyal ginger

          You can use a while loop and use an iterator to achieve this.

          B Offline
          B Offline
          b rad311
          wrote on last edited by
          #4

          Thanks.

          B 1 Reply Last reply
          0
          • B b rad311

            Thanks.

            B Offline
            B Offline
            b rad311
            wrote on last edited by
            #5

            Do you have an example?

            CPalliniC 1 Reply Last reply
            0
            • B b rad311

              Do you have an example?

              CPalliniC Offline
              CPalliniC Offline
              CPallini
              wrote on last edited by
              #6

              vector <double> vt;
              double x;
              //...
              auto it = vt.begin(); // with older compilers use: vector<double>iterator it = vt.begin();
              while (it != vt.end())
              {
              *it /= x;
              it++;
              }

              If the Lord God Almighty had consulted me before embarking upon the Creation, I would have recommended something simpler. -- Alfonso the Wise, 13th Century King of Castile.
              This is going on my arrogant assumptions. You may have a superb reason why I'm completely wrong. -- Iain Clarke
              [My articles]

              In testa che avete, signor di Ceprano?

              B 1 Reply Last reply
              0
              • CPalliniC CPallini

                vector <double> vt;
                double x;
                //...
                auto it = vt.begin(); // with older compilers use: vector<double>iterator it = vt.begin();
                while (it != vt.end())
                {
                *it /= x;
                it++;
                }

                If the Lord God Almighty had consulted me before embarking upon the Creation, I would have recommended something simpler. -- Alfonso the Wise, 13th Century King of Castile.
                This is going on my arrogant assumptions. You may have a superb reason why I'm completely wrong. -- Iain Clarke
                [My articles]

                B Offline
                B Offline
                b rad311
                wrote on last edited by
                #7

                Thanks!

                B 1 Reply Last reply
                0
                • B b rad311

                  Thanks!

                  B Offline
                  B Offline
                  b rad311
                  wrote on last edited by
                  #8

                  Hi, I'm getting the following error:

                  error C2677: binary '/=' : no global operator found which takes type 'std::vector<_Ty>' (or there is no acceptable conversion)

                  CPalliniC 1 Reply Last reply
                  0
                  • B b rad311

                    Hi, How would I take my vector of doubles and divide each element in the vector by a scalar (without using a for loop and explicitly referring to each element using the loop index)? I tried vec/scalar but that doesn't work.

                    A Offline
                    A Offline
                    Aescleal
                    wrote on last edited by
                    #9

                    Look at std::transform, it is your friend when you want to operate on all elements of a collection. And once you've worked out how to do that you can implement your own scalar division operator for collections:

                    template <typename collection>
                    collection operator/( const collection &c, typename collection::value_type divisor )
                    {
                    collection transformed;
                    std::transform( c.begin(), c.end(), std::back_inserter( transformed ), [divisor]( collection::value_type to_divide) { return to_divide/divisor } );
                    return transformed;
                    }

                    This code will only work on a compiler that understands lamdas - VC2008 and earlier don't so you'll have to use a separate class or function to do the fourth term of std::transform. Cheers, Ash

                    S B 2 Replies Last reply
                    0
                    • B b rad311

                      Hi, How would I take my vector of doubles and divide each element in the vector by a scalar (without using a for loop and explicitly referring to each element using the loop index)? I tried vec/scalar but that doesn't work.

                      S Offline
                      S Offline
                      Stephen Hewitt
                      wrote on last edited by
                      #10

                      Here's one way:

                      // Console.cpp : Defines the entry point for the console application.
                      //

                      #include "stdafx.h"
                      #include <iostream>
                      #include <vector>
                      #include <algorithm>
                      #include <iterator>
                      #include <functional>

                      int _tmain(int argc, _TCHAR* argv[])
                      {
                      using namespace std;

                      // Create and fill a vector.
                      vector<double> nums;
                      for (int i=1; i<=10; ++i)
                      	nums.push\_back(i);
                      
                      // Print out the vector's contents.
                      cout << "Before: ";
                      copy(nums.begin(), nums.end(), ostream\_iterator<double>(cout, " "));
                      cout << endl << endl;
                      
                      // Divide all elements by two.
                      transform(
                      	nums.begin(), nums.end(),
                      	nums.begin(),
                      	bind2nd(divides<double>(), 2.0)
                      	);
                      
                      // Print out the vector's contents.
                      cout << "After: ";
                      copy(nums.begin(), nums.end(), ostream\_iterator<double>(cout, " "));
                      cout << endl << endl;
                      
                      return 0;
                      

                      }

                      Steve

                      B 1 Reply Last reply
                      0
                      • A Aescleal

                        Look at std::transform, it is your friend when you want to operate on all elements of a collection. And once you've worked out how to do that you can implement your own scalar division operator for collections:

                        template <typename collection>
                        collection operator/( const collection &c, typename collection::value_type divisor )
                        {
                        collection transformed;
                        std::transform( c.begin(), c.end(), std::back_inserter( transformed ), [divisor]( collection::value_type to_divide) { return to_divide/divisor } );
                        return transformed;
                        }

                        This code will only work on a compiler that understands lamdas - VC2008 and earlier don't so you'll have to use a separate class or function to do the fourth term of std::transform. Cheers, Ash

                        S Offline
                        S Offline
                        Stephen Hewitt
                        wrote on last edited by
                        #11

                        Time to whip out a lambda function...

                        Steve

                        A 1 Reply Last reply
                        0
                        • S Stephen Hewitt

                          Time to whip out a lambda function...

                          Steve

                          A Offline
                          A Offline
                          Aescleal
                          wrote on last edited by
                          #12

                          Using a Lambda here was a bit pointless, I've been so completely wrapped up in saying "Coo, aren't lambda's wonderful?" that I'd completely forgotten about std::divide which is a fair bit easier to read. Although they do get rid of the need to do the std::bind2nd, which can only be a good thing! Cheers, Ash

                          S 1 Reply Last reply
                          0
                          • B b rad311

                            Hi, I'm getting the following error:

                            error C2677: binary '/=' : no global operator found which takes type 'std::vector<_Ty>' (or there is no acceptable conversion)

                            CPalliniC Offline
                            CPalliniC Offline
                            CPallini
                            wrote on last edited by
                            #13

                            The following compiles (and runs) fine (I've a rather old VS2005 compiler...)

                            #include <iostream>
                            #include <vector>
                            using namespace std;

                            int main()
                            {
                            vector <double> vt;

                            vt.push_back(7.0);
                            vt.push_back(5.0);
                            vt.push_back(3.0);

                            double x = 5.0;

                            vector<double>::iterator it = vt.begin();
                            while (it != vt.end())
                            {
                            *it /= x;
                            cout << *it << endl;
                            it++;
                            }
                            }

                            If the Lord God Almighty had consulted me before embarking upon the Creation, I would have recommended something simpler. -- Alfonso the Wise, 13th Century King of Castile.
                            This is going on my arrogant assumptions. You may have a superb reason why I'm completely wrong. -- Iain Clarke
                            [My articles]

                            In testa che avete, signor di Ceprano?

                            B 1 Reply Last reply
                            0
                            • A Aescleal

                              Using a Lambda here was a bit pointless, I've been so completely wrapped up in saying "Coo, aren't lambda's wonderful?" that I'd completely forgotten about std::divide which is a fair bit easier to read. Although they do get rid of the need to do the std::bind2nd, which can only be a good thing! Cheers, Ash

                              S Offline
                              S Offline
                              Stephen Hewitt
                              wrote on last edited by
                              #14

                              I don't know, many people who aren't use to functional programming and function objects find the bind2nd and divides stuff perplexing. Even if you're use to it, if the logic gets even moderately more complex it gets very arcane and the lamda expression will be a lot simpler. My concern is that barely any people would be using a compiler that supports them yet.

                              Steve

                              A 1 Reply Last reply
                              0
                              • S Stephen Hewitt

                                I don't know, many people who aren't use to functional programming and function objects find the bind2nd and divides stuff perplexing. Even if you're use to it, if the logic gets even moderately more complex it gets very arcane and the lamda expression will be a lot simpler. My concern is that barely any people would be using a compiler that supports them yet.

                                Steve

                                A Offline
                                A Offline
                                Aescleal
                                wrote on last edited by
                                #15

                                One advantage Lambdas have over a lot of other C++ features that have been introduced in the past is that two of the more mainstream compilers are supporting them before the C++0x standard's even been voted in. Compare that to the 5 year lag a certain compiler manufacturer had with the last standard and I'm hopeful they'll be mainstream fairly soon. Having said that I'm depressed at the number of people using VC++ 6 on this board so maybe by 2020 we'll see the mainstream get there :-) Cheers, Ash - who doesn't usually hijack threads like this

                                1 Reply Last reply
                                0
                                • CPalliniC CPallini

                                  The following compiles (and runs) fine (I've a rather old VS2005 compiler...)

                                  #include <iostream>
                                  #include <vector>
                                  using namespace std;

                                  int main()
                                  {
                                  vector <double> vt;

                                  vt.push_back(7.0);
                                  vt.push_back(5.0);
                                  vt.push_back(3.0);

                                  double x = 5.0;

                                  vector<double>::iterator it = vt.begin();
                                  while (it != vt.end())
                                  {
                                  *it /= x;
                                  cout << *it << endl;
                                  it++;
                                  }
                                  }

                                  If the Lord God Almighty had consulted me before embarking upon the Creation, I would have recommended something simpler. -- Alfonso the Wise, 13th Century King of Castile.
                                  This is going on my arrogant assumptions. You may have a superb reason why I'm completely wrong. -- Iain Clarke
                                  [My articles]

                                  B Offline
                                  B Offline
                                  b rad311
                                  wrote on last edited by
                                  #16

                                  Thanks for checking, could just be some weird option in my compiler.

                                  1 Reply Last reply
                                  0
                                  • S Stephen Hewitt

                                    Here's one way:

                                    // Console.cpp : Defines the entry point for the console application.
                                    //

                                    #include "stdafx.h"
                                    #include <iostream>
                                    #include <vector>
                                    #include <algorithm>
                                    #include <iterator>
                                    #include <functional>

                                    int _tmain(int argc, _TCHAR* argv[])
                                    {
                                    using namespace std;

                                    // Create and fill a vector.
                                    vector<double> nums;
                                    for (int i=1; i<=10; ++i)
                                    	nums.push\_back(i);
                                    
                                    // Print out the vector's contents.
                                    cout << "Before: ";
                                    copy(nums.begin(), nums.end(), ostream\_iterator<double>(cout, " "));
                                    cout << endl << endl;
                                    
                                    // Divide all elements by two.
                                    transform(
                                    	nums.begin(), nums.end(),
                                    	nums.begin(),
                                    	bind2nd(divides<double>(), 2.0)
                                    	);
                                    
                                    // Print out the vector's contents.
                                    cout << "After: ";
                                    copy(nums.begin(), nums.end(), ostream\_iterator<double>(cout, " "));
                                    cout << endl << endl;
                                    
                                    return 0;
                                    

                                    }

                                    Steve

                                    B Offline
                                    B Offline
                                    b rad311
                                    wrote on last edited by
                                    #17

                                    Thanks Steve!

                                    1 Reply Last reply
                                    0
                                    • A Aescleal

                                      Look at std::transform, it is your friend when you want to operate on all elements of a collection. And once you've worked out how to do that you can implement your own scalar division operator for collections:

                                      template <typename collection>
                                      collection operator/( const collection &c, typename collection::value_type divisor )
                                      {
                                      collection transformed;
                                      std::transform( c.begin(), c.end(), std::back_inserter( transformed ), [divisor]( collection::value_type to_divide) { return to_divide/divisor } );
                                      return transformed;
                                      }

                                      This code will only work on a compiler that understands lamdas - VC2008 and earlier don't so you'll have to use a separate class or function to do the fourth term of std::transform. Cheers, Ash

                                      B Offline
                                      B Offline
                                      b rad311
                                      wrote on last edited by
                                      #18

                                      Thanks for your help Ash. I'm currently doing the following and it works! However, how could I send "op_divide" another parameter? I don't always want to divide by "5", I'd like to send "op_divide" the denominator to use.

                                      long double op_divide (long double d) { return d/5; }
                                      transform (vec1.begin(), vec1.end(), vec2.begin(), op_divide);

                                      Thanks!

                                      A 1 Reply Last reply
                                      0
                                      • B b rad311

                                        Thanks for your help Ash. I'm currently doing the following and it works! However, how could I send "op_divide" another parameter? I don't always want to divide by "5", I'd like to send "op_divide" the denominator to use.

                                        long double op_divide (long double d) { return d/5; }
                                        transform (vec1.begin(), vec1.end(), vec2.begin(), op_divide);

                                        Thanks!

                                        A Offline
                                        A Offline
                                        Aescleal
                                        wrote on last edited by
                                        #19

                                        You're using a function with a hardcoded divisor in it, so the problem is how to get a second parameter into it. If you want to keep using a function then you can expand your function to take a second parameter:

                                        long double op_divide( long double numerator, long double denominator ) { return numerator/denominator; }

                                        and use std::bind2nd to create a function object to pass to transform:

                                        transform( vec.begin(), vec1.end(), vec2.begin(), std::bind2nd( op_divide, 5.0 ) );

                                        [That's unchecked BTW, I'm not on a computer with a compiler on to check it - I'm pretty sure it will though.] If you're doing that you could try using std::divides which does the same thing and saves writing the function. Cheers, Ash

                                        B 1 Reply Last reply
                                        0
                                        • A Aescleal

                                          You're using a function with a hardcoded divisor in it, so the problem is how to get a second parameter into it. If you want to keep using a function then you can expand your function to take a second parameter:

                                          long double op_divide( long double numerator, long double denominator ) { return numerator/denominator; }

                                          and use std::bind2nd to create a function object to pass to transform:

                                          transform( vec.begin(), vec1.end(), vec2.begin(), std::bind2nd( op_divide, 5.0 ) );

                                          [That's unchecked BTW, I'm not on a computer with a compiler on to check it - I'm pretty sure it will though.] If you're doing that you could try using std::divides which does the same thing and saves writing the function. Cheers, Ash

                                          B Offline
                                          B Offline
                                          b rad311
                                          wrote on last edited by
                                          #20

                                          Thanks Ash. I implemented the code, but it is giving many errors, the first being:

                                          error C2825: '_Fn2': must be a class or namespace when followed by '::'

                                          and the 2nd:

                                          error C2039: 'first_argument_type' : is not a member of '`global namespace''

                                          A 1 Reply Last reply
                                          0
                                          Reply
                                          • Reply as topic
                                          Log in to reply
                                          • Oldest to Newest
                                          • Newest to Oldest
                                          • Most Votes


                                          • Login

                                          • Don't have an account? Register

                                          • Login or register to search.
                                          • First post
                                            Last post
                                          0
                                          • Categories
                                          • Recent
                                          • Tags
                                          • Popular
                                          • World
                                          • Users
                                          • Groups