Matrix, Vector, Multiplication [closed] - matrix

Closed. This question is not about programming or software development. It is not currently accepting answers.
This question does not appear to be about a specific programming problem, a software algorithm, or software tools primarily used by programmers. If you believe the question would be on-topic on another Stack Exchange site, you can leave a comment to explain where the question may be able to be answered.
Closed 2 months ago.
Improve this question
I understand what Vector and matrix are.
But I don't know what is vector-matrix multiplication for? How the mathematician come up this theory?
What is matrix-matrix multiplication for? How come up this theory?
I know how to calculate them, but no idea what it looks like in a 3D space.
Can I understand that: Matrix Multiplication is: First we break one of two Matrixes to several vectors; Second, we do Vector-Matrix Multiplication and then adding all of them together?
Thank you for your explanation

Basics
Matrices can map numbers in 2 dimensions. This video shows a good example of how to calculate with matrices.
Matrix A = items sold per day (5 x 3 dimension)
c
o
o c
k a p
i k i
e e e
s s s
monday [ 3 5 3 ]
tuesday [ 7 1 2 ]
wednesday [ 2 5 3 ]
thursday [ 5 4 0 ]
friday [ 3 4 4 ]
Matrix B = Price per item (3 x 1 dimension)
€
cookies [ 4 ]
cakes [ 10 ]
pies [ 8 ]
In order to be able to multiply 2 matrices, the 2nd dimension of the 1st matrix MUST match the 1st dimension of the 2nd matrix (5 x 3) * (3 x 1) (3's must match), and this multiplication will result in a 5 x 1 matrix.
In this example we're multiplying a (days/item) matrix with a (items/price) matrix, and we're expecting a (days/price) matrix that indicates how much we earn per day.
You can immediately see why the numbers of columns of the first matrix must match the number of rows of the second matrix here.
Multiplication
In order to multiply the matrices, we first position them in a better way:
€
[ 4 ]
[ 10 ]
[ 8 ]
monday [ 3 5 3 ] [ ]
tuesday [ 7 1 2 ] [ ]
wednesday [ 2 5 3 ] [ ]
thursday [ 5 4 0 ] [ ]
friday [ 3 4 4 ] [ ]
As demonstrated below, each element in the resulting matrix is the sum of following multiplications:
€
---[ 4 ]
╱ --[ 10 ]
╱ ╱ -[ 8 ]
╱ ╱ ╱ |
╱ ╱ ╱ |
monday [ 3 5 3 ] [ ]
tuesday [ 7 1 2 ] [ ]
wednesday [ 2 5 3 ] - [ 82 ]
thursday [ 5 4 0 ] [ ]
friday [ 3 4 4 ] [ ]
So for the third element, the result is as follows:
2 cookies * 4 €/cookie + 5 cakes * 10 €/cake + 3 pies * 8 €/pie = 82 €
Extending the example
If you also want to know how much time you're spending to bake the stuff you're selling, you can add those numbers to the second matrix as well:
€ min.
cookies [ 4 2 ]
cakes [ 10 30 ]
pies [ 8 20 ]
Multiplying them:
€ min
---[ 4 2 ]
╱ --[ 10 30 ]
╱ ╱ -[ 8 20 ]
╱ ╱ ╱ | |
╱ ╱ ╱ | |
monday [ 3 5 3 ] [ ]
tuesday [ 7 1 2 ] [ ]
wednesday [ 2 5 3 ] - [ 82 214 ]
thursday [ 5 4 0 ] [ ]
friday [ 3 4 4 ] [ ]
Will give you
R(3,2) = 2 * 2 + 5 * 30 + 3 * 20 = 214
So as a result, you know your earnings per day, and your spent minutes per day for the items you sell

Related

shift position in matrix

I have a n x 1 matrix. I'm trying to find a way to "shift" all the elements position (loosing the last element) and then add an element in position 0,0 in this way:
From
[[ 10 ]
[ 5 ]
[ 2 ]
[ 3 ]
[ 1 ]
[ 5 ]]
to (adding a new element 2 in position 0,0)
[[ 2 ]
[ 10 ]
[ 5 ]
[ 2 ]
[ 3 ]
[ 1 ]]
I'm pretty close to the solution but I don't know how add elements to a nested list.
;initial matrix
set mymatrix matrix:from-column-list [[10 5 2 3 1 5]]
;temp
let list matrix:to-column-list mymatrix
let tmplist matrix:to-column-list states
; ERROR here: the result of fput is [2[10 5 2 3 1 5]]
set tmplist fput 2 tmplist
;new matrix
matrix:set-column mymatrix 0 tmplist
EDIT: I realized that indeed for my needs a matrix is an overkill. I solved switching to pure netlogo lists and doing my business in map-reduce.
If you just need elementwise multiplication of objects that are fundamentally one-dimensional, just use map.
Example: (map * [1 2] [3 4]) reports [3 8].
Now you can just do your bookkeeping with lists, which is much easier.
Even if (for some reason you have not stated) you really need matrix operations elsewhere, you almost surely should use lists for the bookkeeping you describe and then convert when necessary.

Mapping from "int" to corresponding permutation value?

I ran across this question this morning.
Basically that question is about data which has to create permutations for 6 values; each one ranging from 1 to 38.
So, first permutation would be
1 1 1 1 1 1 [ permutation 1 ]
1 1 1 1 1 2 [ permutation 2 ]
1 1 1 1 1 3... [ permutation 3 ]
to end much later with
38 38 38 38 38 38 [ permutation 38^^6 ]
The output is simply created by 6 nested loops, each counting from 1 to 38; and within the inner-most loop, you print the 6 loop counters.
Now I am wondering about the math behind that; and out of curiosity: what would be the "function" that
computes the "permutation index", given a any permutation 1 2 3 4 5 6
Probably more interesting: that takes an "index", such as 102382; and tells me the corresponding permutation output
Any idea anybody?
It works exactly like a change of base (binar, octal or hex).
The first one question simply:
1*38^6 + 2*38^5 + 3*38^4 + 4*38^3 +...+6*38^0
The second one reversed:
102382 mod 38... recursively
UPDATE
Let us assume we want change 10 to base 2:
10/2=5 remainder(modulus) **0**
5/2=2 remainder **1**
2/2=1 remainder **0**
1/2=0 remainder **1**
backwards is 1010
general gave a M to change in base B, just divide M by B , and the remainder are going to be the digit in the new base

How to make a matrix of random values in NetLogo?

Is there a way to easily make an $n \cross m$ matrix in NetLogo? Additionally would it be possible to fill this matrix with random values? Thanks.
this answer has been updated for NetLogo 6 task syntax
See http://ccl.northwestern.edu/netlogo/docs/matrix.html for docs on NetLogo's matrix extension.
For creating a matrix, there are several primitives that do that: matrix:make-constant, matrix:make-identity, matrix:from-row-list, matrix:from-column-list.
For creating a matrix and filling it with random values, I'd suggest defining this procedure first:
to-report fill-matrix [n m generator]
report matrix:from-row-list n-values n [n-values m [runresult generator]]
end
Then to make, say, a 5 by 5 matrix, of, say, random integers in the range 0 to 9, it's:
fill-matrix 5 5 [-> random 10]
Example result:
observer> show fill-matrix 5 5 [-> random 10]
observer: {{matrix: [ [ 5 9 3 2 6 ][ 5 8 2 8 0 ][ 6 7 3 7 4 ][ 7 0 4 6 3 ][ 7 9 0 0 5 ] ]}}

Solving a recreational square packing problem

I was asked to find a 11x11-grid containing the digits such that one can read the squares of 1,...,100. Here read means that you fix the starting position and direction (8 possibilities) and if you can find for example the digits 1,0,0,0,0,4 consecutively, you have found the squares of 1, 2, 10, 100 and 20. I made a program (the algorithm is not my own. I modified slightly a program which uses best-first search to find a solution but it is too slow. Does anyone know a better algorithm to solve the problem?
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <vector>
#include <algorithm>
using namespace std;
int val[21][21];//number which is present on position
int vnum[21][21];//number of times the position is used - useful if you want to backtrack
//5 unit borders
int mx[4]={-1,0,1,0};//movement arrays
int my[4]={0,-1,0,1};
int check(int x,int y,int v,int m)//check if you can place number - if you can, return number of overlaps
{
int c=1;
while(v)//extract digits one by one
{
if(vnum[x][y] && (v%10)!=val[x][y])
return 0;
if(vnum[x][y])
c++;
v/=10;
x+=mx[m];
y+=my[m];
}
return c;
}
void apply(int x,int y,int v,int m)//place number - no sanity checks
{
while(v)//extract digits one by one
{
val[x][y]=v%10;
vnum[x][y]++;
v/=10;
x+=mx[m];
y+=my[m];
}
}
void deapply(int x,int y,int v,int m)//remove number - no sanity checks
{
while(v)
{
vnum[x][y]--;
v/=10;
x+=mx[m];
y+=my[m];
}
}
int best=100;
void recur(int num)//go down a semi-random path
{
if(num<best)
{
best=num;
if(best)
printf("FAILED AT %d\n",best);
else
printf("SUCCESS\n");
for(int x=5;x<16;x++) // 16 and 16
{
for(int y=5;y<16;y++)
{
if(vnum[x][y]==0)
putchar('.');
else
putchar(val[x][y]+'0');
}
putchar('\n');
}
fflush(stdout);
}
if(num==0)
return;
int s=num*num,t;
vector<int> poss;
for(int x=5;x<16;x++)
for(int y=5;y<16;y++)
for(int m=0;m<4;m++)
if(t=check(x,y,s,m))
poss.push_back((x)|(y<<8)|(m<<16)|(t<<24));//compress four numbers into an int
if(poss.size()==0)
return;
sort(poss.begin(),poss.end());//essentially sorting by t
t=poss.size()-1;
while(t>=0 && (poss[t]>>24)==(poss.back()>>24))
t--;
t++;
//t is now equal to the smallest index which has the maximal overlap
t=poss[rand()%(poss.size()-t)+t];//select random index>=t
apply(t%256,(t>>8)%256,s,(t>>16)%256);//extract random number
recur(num-1);//continue down path
}
int main()
{
srand((unsigned)time(0));//seed
while(true)
{
for(int i=0;i<21;i++)//reset board
{
memset(val[i],-1,21*sizeof(int));
memset(vnum[i],-1,21*sizeof(int));
}
for(int i=5;i<16;i++)
{
memset(val[i]+5,0,11*sizeof(int));
memset(vnum[i]+5,0,11*sizeof(int));
}
recur(100);
}
}
Using a random search so far I only got to 92 squares with one unused spot (8 missing numbers: 5041 9025 289 10000 4356 8464 3364 3249)
1 5 2 1 2 9 7 5 6 9 5
6 1 0 8 9 3 8 4 4 1 2
9 7 2 2 5 0 0 4 8 8 2
1 6 5 9 6 0 4 4 7 7 4
4 4 2 7 6 1 2 9 0 2 2
2 9 6 1 7 8 4 4 0 9 3
6 5 5 3 2 6 0 1 4 0 6
4 7 6 1 8 1 1 8 2 8 1
8 0 1 3 4 8 1 5 3 2 9
0 5 9 6 9 8 8 6 7 4 5
6 6 2 9 1 7 3 9 6 9
The algorithm basically uses as solution encoding a permutation on the input (search space is 100!) and then places each number in the "topmost" legal position. The solution value is measured as the sum of the squares of the lengths of the numbers placed (to give more importance to long numbers) and the number of "holes" remaining (IMO increasing the number of holes should raise the likehood that another number will fit in).
The code has not been optimized at all and is only able to decode a few hundred solutions per second. Current solution has been found after 196k attempts.
UPDATE
Current best solution with this approach is 93 without free holes (7 missing numbers: 676 7225 3481 10000 3364 7744 5776):
9 6 0 4 8 1 0 0 9 3 6
6 4 0 0 2 2 5 6 8 8 9
1 7 2 9 4 1 5 4 7 6 3
5 8 2 3 8 6 4 9 6 5 7
2 4 4 4 1 8 2 8 2 7 2
1 0 8 9 9 1 3 4 4 9 1
2 1 2 9 6 1 0 6 2 4 1
2 3 5 5 3 9 9 4 0 9 6
5 0 0 6 1 0 3 5 2 0 3
2 7 0 4 2 2 5 2 8 0 9
9 8 2 2 6 5 3 4 7 6 1
This is a solution (all 100 numbers placed) however using a 12x12 grid (MUCH easier)
9 4 6 8 7 7 4 4 5 5 1 7
8 3 0 5 5 9 2 9 6 7 6 4
4 4 8 3 6 2 6 0 1 7 8 4
4 8 4 2 9 1 4 0 5 6 1 4
9 1 6 9 4 8 1 5 4 2 0 1
9 4 4 7 2 2 5 2 2 5 0 0
4 6 2 2 5 8 4 2 7 4 0 2
0 3 3 3 6 4 0 0 6 3 0 9
9 8 0 1 2 1 7 9 5 5 9 1
6 8 4 2 3 5 2 6 3 2 0 6
9 9 8 2 5 2 9 9 4 2 2 7
1 1 5 6 6 1 9 3 6 1 5 4
It has been found using a truly "brute force" approach, starting from a random matrix and keeping randomly changing digits when that improved the coverage.
This solution has been found by an highly unrolled C++ program automatically generated by a Python script.
Update 2
Using an incremental approach (i.e. keeping a more complex data structure so that when changing a matrix element the number of targets covered can be updated instead than recomputed) I got a much faster search (about 15k matrices/second investigated with a Python implementation running with PyPy).
In a few minutes this version was able to find a 99 quasi-solution (a number is still missing):
7 0 5 6 5 1 1 5 7 1 6
4 6 3 3 9 8 8 6 7 6 1
3 9 0 8 2 6 1 1 4 7 8
1 1 0 8 9 9 0 0 4 4 6
3 4 9 0 4 9 0 4 6 7 1
6 4 4 6 8 6 3 2 5 2 9
9 7 8 4 1 1 4 0 5 4 2
6 2 4 1 5 2 2 1 2 9 7
9 8 2 5 2 2 7 3 6 5 0
3 1 2 5 0 0 6 3 0 5 4
7 5 6 9 2 1 6 5 3 4 6
UPDATE 3
Ok. After a some time (no idea how much) the same Python program actually found a complete solution (several ones indeed)... here is one
6 4 6 9 4 1 2 9 7 3 6
9 2 7 7 4 4 8 1 2 1 7
1 0 6 2 7 0 4 4 8 3 4
2 1 2 2 5 5 9 2 9 6 5
9 2 5 5 2 0 2 6 3 9 1
1 6 3 6 0 0 9 3 7 0 6
6 0 0 4 9 0 1 6 0 0 4
9 8 4 4 8 0 1 4 5 2 3
2 4 8 2 8 1 6 8 6 7 5
1 7 6 9 2 4 5 4 2 7 6
6 6 3 8 8 5 6 1 5 2 1
The searching program can be found here...
You've got 100 numbers and 121 cells to work with, so you'll need to be very efficient. We should try to build up the grid, so that each time we fill a cell, we attain a new number in our list.
For now, let's only worry about 68 4-digit numbers. I think a good chunk of the shorter numbers will be in our grid without any effort.
Start with a 3x3 or 4x4 set of numbers in the top-left of your grid. It can be arbitrary, or fine-tune for slightly better results. Now let's fill in the rest of the grid one square at a time.
Repeat these steps:
Fill an empty cell with a digit
Check which numbers that knocked off the list
If it didn't knock off any 4-digit numbers, try a different digit or cell
Eventually you may need to fill 2 cells or even 3 cells to achieve a new 4-digit number, but this should be uncommon, except at the end (at which point, hopefully there's a lot of empty space). Continue the process for the (few?) remaining 3-digit numbers.
There's a lot room for optimizations and tweaks, but I think this technique is fast and promising and a good starting point. If you get an answer, share it with us! :)
Update
I tried my approach and only got 87 out of the 100:
10894688943
60213136008
56252211674
61444925224
59409675697
02180334817
73260193640
.5476685202
0052034645.
...4.948156
......4671.
My guess is that both algorithms are too slow. Some optimization algorithm might work like best-first search or simulated annealing but my I don't have much experience on programming those.
Have you tried any primary research on Two-Dimensional Bin Packing (2DBP) algorithms? Google Scholars is a good start. I did this a while ago when building an application to generate mosaics.
All rectangular bin packing algorithms can be divided into 4 groups based on their support for the following constraints:
Must the resulting bin be guillotine cuttable? I.e. do you have to later slice the bin(s) in half until all the pieces are unpacked?
Can the pieces be rotated to fit into the bin? Not an issue with square pieces, so this makes more algorithms available to you.
Out of all the algorithms I looked into, the most efficient solution is an Alternate Directions (AD) algorithm with a Tabu Search optimization layer. There are dissertations which prove this. I may be able to dig-up some links if this helps.
Some ideas off the top of my head, without investing much time into thinking about details.
I would start by counting the number of occurrences of each digit in all squares 1..100. The total number of digits will be obviously larger than 121, but by analyzing individual frequencies you can deduce which digits must be grouped on a single line to form as many different squares as possible. For example, if 0 has the highest frequency, you have to try to put as many squares containing a 0 on the same line.
You could maintain a count of digits for each line, and each time you place a digit, you update the count. This lets you easily compute which square numbers have been covered by that particular line.
So, the program will still be brute-force, but it will exploit the problem structure much better.
PS: Counting digit frequencies is the easiest way to decide whether a certain permutation of digits constitutes a square.

Finding the center of a cluster

I have the following problem - made abstract to bring out the key issues.
I have 10 points each which is some distance from the other. I want to
be able to find the center of the cluster i.e. the point for which the pairwise distance to each other point is minimised,
let p(j) ~ p(k) represent the pairwise distance beteen points j and k
p(i) is center-point of the cluster iff p(i) s.t. min[sum(p(j)~p(k))] for all 0 < j,k <= n where we have n points in the cluster
determine how to split the cluster in to two clusters once the number of data points in the cluster goes above some threshold t.
This is not euclidean space. But the distances can be summarised as follows - p(i) is point i:
p(1) p(2) p(3) p(4) p(5) p(6) p(7) p(8) p(9) p(10)
p(1) 0 2 1 3 2 3 3 2 3 4
p(2) 2 0 1 3 2 3 3 2 3 4
p(3) 1 1 0 2 0 1 2 1 2 3
p(4) 3 3 2 0 1 2 3 2 3 4
p(5) 2 2 1 1 0 1 2 1 2 3
p(6) 3 3 2 2 1 0 3 2 3 4
p(7) 3 3 2 3 2 3 0 1 2 3
p(8) 2 2 1 2 1 2 1 0 1 2
p(9) 3 3 2 3 2 3 2 1 0 1
p(10) 4 4 3 4 3 4 3 2 1 0
How would I calculate which is the center point of this cluster?
As far as I understand this looks like K Means Clustering, and what you are looking for is usually known as 'Medoids'.
See here: http://en.wikipedia.org/wiki/Medoids or here: http://en.wikipedia.org/wiki/K-medoids
I may be about to have that frisson that comes just before displaying utter stupidity. But doesn't this yield easily to brute force? In Python:
distances = [
[ 0 , 2 , 1 , 3 , 2 , 3 , 3 , 2 , 3 , 4 , ],
[ 2 , 0 , 1 , 3 , 2 , 3 , 3 , 2 , 3 , 4 , ],
[ 1 , 1 , 0 , 2 , 0 , 1 , 2 , 1 , 2 , 3 , ],
[ 3 , 3 , 2 , 0 , 1 , 2 , 3 , 2 , 3 , 4 , ],
[ 2 , 2 , 1 , 1 , 0 , 1 , 2 , 1 , 2 , 3 , ],
[ 3 , 3 , 2 , 2 , 1 , 0 , 3 , 2 , 3 , 4 , ],
[ 3 , 3 , 2 , 3 , 2 , 3 , 0 , 1 , 2 , 3 , ],
[ 2 , 2 , 1 , 2 , 1 , 2 , 1 , 0 , 1 , 2 , ],
[ 3 , 3 , 2 , 3 , 2 , 3 , 2 , 1 , 0 , 1 , ],
[ 4 , 4 , 3 , 4 , 3 , 4 , 3 , 2 , 1 , 0 , ],
]
currentMinimum = 99999
for point in range ( 10 ) :
distance_sum = 0
for second_point in range ( 10 ) :
if point == second_point : continue
distance_sum += distances [ point ] [ second_point ]
print '>>>>>', point, distance_sum
if distance_sum < currentMinimum :
currentMinimum = distance_sum
centre = point
print centre
a)
find median or average values of all distances. = avgAll
For each p, find average distance to other machines. = avgP(i)
Pick the closer one as center. avgAll ~= avgP(i)
b)
no idea for now..
maybe for each p, find the closer machine.
by this logic make a graph.
than somehow (i dont know yet) divide the graph
What you're trying to do, or at least (b) belongs to Cluster Analysis. A branch of mathematics / statistics / econometrics where datapoints (e.g. points in n-dimensional space) are divided among groups or clusters. How to do this is not a trivial questions, there are many, many possible ways.
Read more at the wikipedia article on cluster analysis.

Resources