ETOOBUSY 🚀 minimal blogging for the impatient
PWC145 - Dot Product
TL;DR
Here we are with TASK #1 from The Weekly Challenge #145. Enjoy!
The challenge
You are given 2 arrays of same size,
@a
and@b
.Write a script to implement
Dot Product
.Example:
@a = (1, 2, 3); @b = (4, 5, 6); $dot_product = (1 * 4) + (2 * 5) + (3 * 6) => 4 + 10 + 18 => 32
The questions
My assumption here is that we are talking about the Dot Product:
In mathematics, the dot product or scalar product is an algebraic operation that takes two equal-length sequences of numbers (usually coordinate vectors), and returns a single number. […] The name “dot product” is derived from the centered dot
·
, that is often used to designate this operation […]
Which implies:
- the two input vectors are from the same vector space or, at least, the two sequences of numbers take elements from the same field;
- the product itself can be defined as follows:
The solution
Raku first, which allows for a very compact solution. We define a
class
for storing vectors, and overload/define an operator ·
to
implement the Dot Product:
#!/usr/bin/env raku
use v6;
class Vector { has @.v; method new (*@x) { self.bless(v => @x) } }
sub infix:<·> (Vector:D $x, Vector:D $y) { ($x.v »*« $y.v).sum }
sub MAIN {
my $a = Vector.new(1, 2, 3);
my $b = Vector.new(4, 5, 6);
put $a · $b;
}
We’re using the »*«
version here to insist that the two sequences of
numbers at both ends have the same number of elements. In case they
don’t… it will complain loudly.
The translation into Perl is more… lower level, but still we can overload something to represent the operation:
#!/usr/bin/env perl
use v5.24;
use warnings;
use experimental 'signatures';
no warnings 'experimental::signatures';
my $v = Vector->new(1, 2, 3);
my $w = Vector->new(4, 5, 6);
say $v . $w;
package Vector;
use v5.24;
use experimental 'signatures';
no warnings 'experimental::signatures';
use overload
'.' => sub ($v, $w, @rest) {
die "size mismatch\n" unless $v->$#* == $w->$#*;
my $dp = 0;
$dp += $v->[$_] * $w->[$_] for 0 .. $v->$#*;
return $dp;
};
sub new ($package, @a) { bless \@a, $package }
In this case we have to explicitly check for matching sizes of the
underlying arrays and possibly die
if they are not the same.
Stay safe and mathy, people!