I am writing a program that is a Game of Thrones Game similar to minesweeper. The user is asked for the size of the kingdom and depending on the size has a certain amount of knights. I create a matrix (size by size) of zeros to pre-allocate and assign the same amount of kings as there are knights to random places in the matrix. I now have made a new function that i call in the main script that i want to iterate through the matrix and assign new values to each element based on how many kings are in the neighboring spots for example:
_ 1 2 3 4 5 6 7 8
1 * 1 1 1 1 0 0 0
2 1 2 2 * 2 2 1 1
3 1 2 * 3 * 2 * 1
4 * 3 1 2 1 2 1 1
5 * 2 0 0 0 0 0 0
6 1 0 0 1 1 2 1 1
7 1 1 1 1 * 2 * 1
8 1 * 1 1 1 2 1 1
The problem is I really do not know how to actually count the neighboring kings and change the values in my matrix. I have started with some for loops for the sides but i am not sure how to proceed. The main scrips and the function are bellow Thank you!
Main Script:
clear all;close all;clc;
%display menu of options to play gam or exit
choice = menu('Choose an option', 'Exit Program', 'Start New Game');
%choise 1 is to exit the program
while choice ~= 1
switch choice
case 0
disp('Error - please choose one of the options.')
choice = menu('Choose an option', 'Exit Program', 'Start New Game');
%choice two is to start a new game
case 2
disp('Welcome to the GAME of THRONES!');
name = input('State your name, Your Grace: ','s');
size = input(['How vast is your Kindom ', name , ' your Grace?: ']);
Kings = floor((size^2)/6);
A = [name, ' Your Grace, you have ' num2str(Kings), ' Knights left to defeat ' num2str(Kings), ' Kings'];
disp(A);
game_choices = menu('Choose an option','Show the Kingdoms','Enter a new Coordinat');
switch game_choices
case 1 %Show the board
mymat = zeros(size);%matrix of users size
Kr=randsample(size^2,Kings);%vector of random positions for the kings
for i= 1:Kings
mymat([Kr(i)])=999;%put kings into mat of zeros in there random assignments
end
makeBoard(size);
%cell array game board
case 2 %enter a new coordinate
end
end
choice = menu('Choose an option', 'Exit Program', 'Start New Game');
end
Function i do not know how to write:
function [ mymatG ] = countTheKings( mymat )
%this function counts the kings and puts the numbers where they should be
%should have 2 for loops
for i = 1:size
for j = 1:size
%top
mymat(1,j)=
%bottom
mymat(size,j)=
%left side
mymat(i,1)=
%right side
mymat(i,size)=
end
A classic way to count the number of neighbors is to use convolution. 2D Convolution, in the discrete world, shifts a matrix ("kernel") over a bigger matrix and for each shift, the overlap is computed. The overlap is defined as the sum of the element-wise multiplication of the kernel and the data underneath of it. The resulting value is then used to replace the value that the kernel is centered on.
We can design the kernel to "detect" neighbors. We want it to have ones in spots that you consider to be neighbors and zeros in spots that you don't consider to be neighbors. This would probably look like this if you don't want your kings to consider themselves a neighbor.
1 1 1
1 0 1
1 1 1
This matrix will be centered at every point on your board and element-wise multiplication with the board will be performed and all elements will be summed up.
For example, if this was centered at the following data
1 2 3
4 5 6
7 8 9
It would be processed as:
(1 * 1) + (2 * 1) + (3 * 1) + (4 * 1) + (5 * 0) + (6 * 1) + (7 * 1) + (8 * 1) + (9 * 1)
1 + 2 + 3 + 4 + 0 + 6 + 7 + 8 + 9
40
So we can also use convolution of this "kernel" to count the number of 1's in a binary matrix.
So for this data
1 0 1
0 0 0
1 0 0
When we apply our kernel to this we get
(1 * 1) + (0 * 1) + (1 * 1) + (0 * 1) + (0 * 0) + (0 * 1) + (1 * 1) + (0 * 1) + (0 * 1)
1 + 0 + 1 + 0 + 0 + 0 + 1 + 0 + 0
3
If you imagine that the binary data we applied this kernel to was 1 where there is a king and 0 where there isn't, this is the number of kings that surround a given element.
So what we can do is take the kernel from the beginning of our question, and create a binary matrix that is 1's where there is a king and 0's otherwise. The result will be the size of your board and the values will be the number of neighboring kings.
kernel = [1 1 1;
1 0 1;
1 1 1];
mymat = [9 0 0 0 0 0 0 0
0 0 0 9 0 0 0 0
0 0 9 0 9 0 9 0
9 0 0 0 0 0 0 0
9 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0
0 0 0 0 9 0 9 0
0 9 0 0 0 0 0 0];
isKing = mymat == 9;
nKingNeighbors = conv2(double(isKing), kernel, 'same');
%// 0 1 1 1 1 0 0 0
%// 1 2 2 2 2 2 1 1
%// 1 2 1 3 1 2 0 1
%// 1 3 1 2 1 2 1 1
%// 1 2 0 0 0 0 0 0
%// 1 1 0 1 1 2 1 1
%// 1 1 1 1 0 2 0 1
%// 1 0 1 1 1 2 1 1
If you didn't want to consider diagonal entries to be neighbors you could simply change your kernel to be.
0 1 0
1 0 1
0 1 0
So if we take this back to your example, we could write your countTheKings function as
function mymatG = countTheKings(mymat)
kernel = [1 1 1
1 0 1
1 1 1];
mymatG = conv2(double(mymat == 999), kernel, 'same');
end
Here is an animation showing what the 2D convolution is actually doing. The kernel is shown in red and you can see the values of nKingNeighbors being filled in as the kernel is shifted over the image.
I am trying to solve the problem http://postimg.org/image/4bmfha8m7/
I am having trouble in implementing the weight matrix for the 36 inputs.
I have a 3 neuron hidden layer.
I use the backpropagation algorithm to learn.
What I have tried so far is:
% Sigmoid Function Definition
function [result] = sigmoid(x)
result = 1.0 ./ (1.0 + exp(-x));
end
% Inputs
input = [1 1 0 1 1 1 0 1 0 1 0 1 1 1 0 0 0 0 0 0 0 1 1 1 0 0 1 1 1 0 0 1 1 1 0;
0 0 0 0 1 0 1 1 1 0 0 1 1 1 0 0 0 0 0 1 0 1 1 1 0 0 1 1 1 0 0 0 0 0 1;
0 0 0 0 0 0 1 1 1 1 0 1 1 1 1 0 1 1 1 1 0 1 1 1 1 0 1 1 1 1 0 0 0 0 0;
0 0 0 0 1 0 1 1 1 0 0 1 1 1 0 0 1 1 1 0 0 1 1 1 0 0 1 1 1 0 0 0 0 0 1];
% Desired outputs
output = [1;1;1;1];
% Initializing the bias (Bias or threshold are the same thing, essential for learning, to translate the curve)
% Also, the first column of the weight matrix is the weight of the bias values
bias = [-1 -1 -1 -1];
% Learning coefficient
coeff = 1.0;
% Number of learning iterations
iterations = 100;
disp('No. Of Learning Iterations = ');
disp(iterations);
% Initial weights
weights = ones(36,36);
% Main Algorithm Begins
for i = 1:iterations
out = zeros(4,1);
numIn = length (input(:,1));
for j = 1:numIn
% 1st neuron in the hidden layer
H1 = bias(1,1)*weights(1,1) + input(j,1)*weights(1,2) + input(j,2)*weights(1,3) + input(j,3)*weights(1,4)+ input(j,4)*weights(1,5) + input(j,5)*weights(1,6) + input(j,6)*weights(1,7)
+ input(j,7)*weights(1,8) + input(j,8)*weights(1,9) + input(j,9)*weights(1,10)+ input(j,10)*weights(1,11) + input(j,11)*weights(1,12) + input(j,12)*weights(1,13)
+ input(j,13)*weights(1,14) + input(j,14)*weights(1,15) + input(j,15)*weights(1,16)+ input(j,16)*weights(1,17) + input(j,17)*weights(1,18) + input(j,18)*weights(1,19)
+ input(j,19)*weights(1,20) + input(j,20)*weights(1,21) + input(j,21)*weights(1,22)+ input(j,22)*weights(1,23) + input(j,23)*weights(1,24) + input(j,24)*weights(1,25)
+ input(j,25)*weights(1,26) + input(j,26)*weights(1,27) + input(j,27)*weights(1,28)+ input(j,28)*weights(1,29) + input(j,29)*weights(1,30) + input(j,30)*weights(1,31)
+ input(j,31)*weights(1,32) + input(j,32)*weights(1,33) + input(j,33)*weights(1,34)+ input(j,34)*weights(1,35) + input(j,35)*weights(1,36)
x2(1) = sigmoid(H1);
% 2nd neuron in the hidden layer
H2 = bias(1,2)*weights(2,1) + input(j,1)*weights(2,2) + input(j,2)*weights(2,3) + input(j,3)*weights(2,4)+ input(j,4)*weights(2,5) + input(j,5)*weights(2,6) + input(j,6)*weights(2,7)
+ input(j,7)*weights(2,8) + input(j,8)*weights(2,9) + input(j,9)*weights(2,10)+ input(j,10)*weights(2,11) + input(j,11)*weights(2,12) + input(j,12)*weights(2,13)
+ input(j,13)*weights(2,14) + input(j,14)*weights(2,15) + input(j,15)*weights(2,16)+ input(j,16)*weights(2,17) + input(j,17)*weights(2,18) + input(j,18)*weights(2,19)
+ input(j,19)*weights(2,20) + input(j,20)*weights(2,21) + input(j,21)*weights(2,22)+ input(j,22)*weights(2,23) + input(j,23)*weights(2,24) + input(j,24)*weights(2,25)
+ input(j,25)*weights(2,26) + input(j,26)*weights(2,27) + input(j,27)*weights(2,28)+ input(j,28)*weights(2,29) + input(j,29)*weights(2,30) + input(j,30)*weights(2,31)
+ input(j,31)*weights(2,32) + input(j,32)*weights(2,33) + input(j,33)*weights(2,34)+ input(j,34)*weights(2,35) + input(j,35)*weights(2,36)
x2(2) = sigmoid(H2);
% 3rd neuron in the hidden layer
H3 = bias(1,3)*weights(3,1) + input(j,1)*weights(3,2) + input(j,2)*weights(3,3) + input(j,3)*weights(3,4)+ input(j,4)*weights(3,5) + input(j,5)*weights(3,6) + input(j,6)*weights(3,7)
+ input(j,7)*weights(3,8) + input(j,8)*weights(3,9) + input(j,9)*weights(3,10)+ input(j,10)*weights(3,11) + input(j,11)*weights(3,12) + input(j,12)*weights(3,13)
+ input(j,13)*weights(3,14) + input(j,14)*weights(3,15) + input(j,15)*weights(3,16)+ input(j,16)*weights(3,17) + input(j,17)*weights(3,18) + input(j,18)*weights(3,19)
+ input(j,19)*weights(3,20) + input(j,20)*weights(3,21) + input(j,21)*weights(3,22)+ input(j,22)*weights(3,23) + input(j,23)*weights(3,24) + input(j,24)*weights(3,25)
+ input(j,25)*weights(3,26) + input(j,26)*weights(3,27) + input(j,27)*weights(3,28)+ input(j,28)*weights(3,29) + input(j,29)*weights(3,30) + input(j,30)*weights(3,31)
+ input(j,31)*weights(3,32) + input(j,32)*weights(3,33) + input(j,33)*weights(3,34)+ input(j,34)*weights(3,35) + input(j,35)*weights(3,36)
x2(3) = sigmoid(H3);
% Output layer
x3_1 = bias(1,4)*weights(4,1) + x2(1)*weights(4,2) + x2(2)*weights(4,3) + x2(3)*weights(4,4);
out(j) = sigmoid(x3_1);
% Adjust delta values of weights
% For output layer: delta(wi) = xi*delta,
% delta = (1-actual output)*(desired output - actual output)
delta3_1 = out(j)*(1-out(j))*(output(j)-out(j));
% Propagate the delta backwards into hidden layers
delta2_1 = x2(1)*(1-x2(1))*weights(3,2)*delta3_1;
delta2_2 = x2(2)*(1-x2(2))*weights(3,3)*delta3_1;
delta2_3 = x2(3)*(1-x2(3))*weights(3,4)*delta3_1;
% Add weight changes to original weights and then use the new weights.
% delta weight = coeff*x*delta
for k = 1:4
if k == 1 % Bias cases
weights(1,k) = weights(1,k) + coeff*bias(1,1)*delta2_1;
weights(2,k) = weights(2,k) + coeff*bias(1,2)*delta2_2;
weights(3,k) = weights(3,k) + coeff*bias(1,3)*delta2_3;
weights(4,k) = weights(4,k) + coeff*bias(1,4)*delta3_1;
else % When k=2 or 3 input cases to neurons
weights(1,k) = weights(1,k) + coeff*input(j,1)*delta2_1;
weights(2,k) = weights(2,k) + coeff*input(j,2)*delta2_2;
weights(3,k) = weights(3,k) + coeff*input(j,3)*delta2_3;
weights(4,k) = weights(4,k) + coeff*x2(k-1)*delta3_1;
end
end
end
end
disp('For the Input');
disp(input);
disp('Output Is');
disp(out);
disp('Test Case: For the Input');
input = [1 1 0 1 1 1 0 1 0 1 0 1 1 1 0 0 0 0 0 0 0 1 1 1 0 0 1 1 1 0 0 1 1 1 0];
For me the problem is the labeling, I can't see where do you have the output
Output (1,1,1,1)? What do you mean. Perhaps I miss something but for me there are two ways of labeling a multiclass clasification one is with a label directly (0 for A, 1 for B, 3 for C...) and expanding it after or directly expanded like A=1,0,0,0 = [1,0,0,0;0,1,0,0;0,0,1,0;0,0,0,1]
The way that you make operations is very easy to make a mistakes, take a look to matlab/octave matrix operations, it's very powerful and could simplify everything a lot.
I need to calculate the following in matlab.
EDIT EDIT: I alway have a 16 x 3 matrix. 16 rows and 3 columns.
The 3 columns represent R,G,B and the 16 rows represent points. From 1-16.
An example matrix looks like this:
1 1 1
-1 0 0
0 0 1
1 0 0
-1 0 0
1 0 -1
1 1 1
1 1 1
0 0 0
-1 0 1
1 0 0
0 0 1
1 0 1
0 0 0
0 0 0
1 0 1
Now I need to know are there 11 coherently rows which have min. 1 value ~= 0 in each column?
In the above example the first 8 rows and the last row have in each column min 1 value and are coherently. So this 9 rows are the max coherently rows without a complete zero row between.
Sry that my first post wasn't correct.
I've do that with a really poor for-solution. Is there a faster way (vectorized) to do that?
for i=1:16
for j=0:16
if i+j > 16
value = (i+j)-16;
else
value = i+j;
end
if table(value,1) ~= 0 || table(value,2) ~= 0 || table(value,3) ~= 0
equal = equal + 1;
if equal >= 11
copy(y,x) = 1;
equal = 0;
break;
end
else
equal = 0;
end
end
end
end
And the 16 points are circular. This min the first point and the last point connect.
Thanks for help and sry for the confusing.
This counts the number of coherent rows with at least one none-zero entry without circularity:
B = ~(A==0);
idx = find(sum(B,2) == 0);
result = max([idx;size(A,1)+1] - [0;idx]) - 1;
Now you can check whether result is bigger than 11.
Another way would be:
B = ~(A==0);
C = bwconncomp(sum(B,2)>0);
num = cellfun(#numel,C.PixelIdxList);
result = max(num);
EDIT 2: To account for circularity, i.e. rows at the beginning and the end should be counted as coherent, you could do
B = ~(A==0);
idx = find(sum(B,2) == 0);
result = max([idx;size(A,1)+idx;size(A,1)+1] - [0;idx;size(A,1)+idx]) - 1;
EDIT: I edited the result-line in the first solution according to Knedlsepp's comments.
This is a somewhat clunky solution, but it should give a solution at least if the matrix isn't too big. If you call your matrix m try the following line of code:
log2(max([cumprod(2*logical(m),2),ones(size(m,1),1)],[],2))
I hope this helps!
EDIT:
Now that it is clear what is ment by the question, here's an answer that should work:
find(~[m(:,1)|m(:,2)|m(:,3);0],1)-1 >= 11