Calcular Ponto Produto de Dois Vectores em C++

Jinku Hu 12 outubro 2023
  1. Utilize std::inner_product para calcular o produto de ponto de dois vectores em C++
  2. Utilize std::transform_reduce para calcular o produto de pontos de dois vectores em C++
  3. Utilizar std::transform_reduce e std::execution::par Calcular Produto Ponto de Dois Vectores
Calcular Ponto Produto de Dois Vectores em C++

Este artigo irá demonstrar múltiplos métodos para calcular o produto ponto de dois vectores em C++.

O produto ponto é a soma dos produtos dos elementos correspondentes dos dois vectores. Suponhamos que temos dois vectores - {1, 2, 3} e {4, 5, 6}, e o produto ponto destes vectores é 1*4 + 2*5 + 3*6 = 32.

Utilize std::inner_product para calcular o produto de ponto de dois vectores em C++

std::inner_product faz parte da biblioteca de algoritmos numéricos C++ incluídos no cabeçalho <numeric>. O método calcula a soma dos produtos em duas gamas, a primeira das quais é especificada com iteradores begin/end e a segunda gama com apenas begin. A função também toma o init como quarto parâmetro para inicializar o valor do acumulador. O valor de retorno é o valor final do produto de ponto das gamas dadas. Note-se que std::inner_product realiza sempre operações numa dada ordem.

#include <iostream>
#include <iterator>
#include <numeric>
#include <vector>

using std::copy;
using std::cout;
using std::endl;
using std::vector;

int main() {
  vector<int> vec1{1, 2, 3, 4, 5};
  vector<int> vec2{2, 4, 6, 8, 10};

  copy(vec1.begin(), vec1.end(), std::ostream_iterator<int>(cout, "; "));
  cout << endl;

  copy(vec2.begin(), vec2.end(), std::ostream_iterator<int>(cout, "; "));
  cout << endl;

  cout << "Scalar product is: "
       << inner_product(vec1.begin(), vec1.end(), vec2.begin(), 0);
  cout << endl;

  return EXIT_SUCCESS;
}

Resultado:

1; 2; 3; 4; 5;
2; 4; 6; 8; 10;
Scalar product is: 110

Utilize std::transform_reduce para calcular o produto de pontos de dois vectores em C++

Ao contrário do método anterior, std::transform_reduce pode realizar operações em intervalos fora de ordem, maximizando assim o desempenho. O método std::transform_reduce é essencialmente a versão paralela do algoritmo std::inner_product. O exemplo seguinte demonstra a execução da função com os mesmos argumentos que foram passados no exemplo anterior.

#include <iostream>
#include <iterator>
#include <numeric>
#include <vector>

using std::copy;
using std::cout;
using std::endl;
using std::inner_product;
using std::vector;

int main() {
  vector<int> vec1{1, 2, 3, 4, 5};
  vector<int> vec2{2, 4, 6, 8, 10};

  copy(vec1.begin(), vec1.end(), std::ostream_iterator<int>(cout, "; "));
  cout << endl;

  copy(vec2.begin(), vec2.end(), std::ostream_iterator<int>(cout, "; "));
  cout << endl;

  cout << "Scalar product is: "
       << std::transform_reduce(vec1.begin(), vec1.end(), vec2.begin(), 0);

  return EXIT_SUCCESS;
}

Resultado:

1; 2; 3; 4; 5;
2; 4; 6; 8; 10;
Scalar product is: 110

Utilizar std::transform_reduce e std::execution::par Calcular Produto Ponto de Dois Vectores

Em alternativa, pode-se especificar adicionalmente uma política de execução para o algoritmo std::transform_reduce. Este método oferece mais controlo ao programador uma vez que o fluxo do programa pode ser personalizado com regras de execução tal como definidas neste manual. Ainda que haja ganhos de desempenho na utilização do transform_reduce, deve-se sempre ter em conta as condições de corrida potenciais ao especificar a política de execução paralela.

#include <execution>
#include <iostream>
#include <iterator>
#include <numeric>
#include <vector>

using std::copy;
using std::cout;
using std::endl;
using std::inner_product;
using std::vector;

int main() {
  vector<int> vec1{1, 2, 3, 4, 5};
  vector<int> vec2{2, 4, 6, 8, 10};

  copy(vec1.begin(), vec1.end(), std::ostream_iterator<int>(cout, "; "));
  cout << endl;

  copy(vec2.begin(), vec2.end(), std::ostream_iterator<int>(cout, "; "));
  cout << endl;

  cout << "Scalar product is: "
       << std::transform_reduce(std::execution::par, vec1.begin(), vec1.end(),
                                vec2.begin(), 0);

  return EXIT_SUCCESS;
}

Resultado:

1; 2; 3; 4; 5;
2; 4; 6; 8; 10;
Scalar product is: 110
Autor: Jinku Hu
Jinku Hu avatar Jinku Hu avatar

Founder of DelftStack.com. Jinku has worked in the robotics and automotive industries for over 8 years. He sharpened his coding skills when he needed to do the automatic testing, data collection from remote servers and report creation from the endurance test. He is from an electrical/electronics engineering background but has expanded his interest to embedded electronics, embedded programming and front-/back-end programming.

LinkedIn Facebook

Artigo relacionado - C++ Vector