Is there a way to reverse the MNIST? - java

I have recently been looking into AI and the MNIST detest. I have decided to create 18 different images in microsoft paint. These images are 28x28, and are named accordingly into the code below. I wanted to see if I could get my network to overfit on a certain set of images in hopes that I can prompt it with the label and have it return the image.
I would give it [[7]], and have it return a 28x28 array of numbers from 1 - 255 denoting the color of the pixel. The only problem is that the network basically doesn't learn. I have also tried putting it in the normal way. I have given it the picture, just like the mnist, and had it return the data of the label. It couldn't even to this. I have the data scaled from 0 - 1 in this network. If anyone can give any imput, that would be great.
import tensorflow as tf
import numpy as np
import cv2
import matplotlib as plt
import os
from PIL import Image
X = np.array([[0.01],[0.02],[0.03],[0.04],[0.05],[0.06],[0.07],[0.08],[0.9],[0.10],[0.11],[0.12],[0.13],[0.14],[0.23],[0.57],[0.64],[0.01]])
#X = np.reshape(X, (-1, 1+18 - 1))
print(np.shape(X))
Y = np.array([[cv2.imread("C:/Users/17324/Downloads/aiFlow/one.png")[:,:,0]], [cv2.imread("C:/Users/17324/Downloads/aiFlow/Two.png")[:,:,0]],
[cv2.imread("C:/Users/17324/Downloads/aiFlow/Three.png")[:,:,0]],[cv2.imread("C:/Users/17324/Downloads/aiFlow/Four.png")[:,:,0]],
[cv2.imread("C:/Users/17324/Downloads/aiFlow/Five.png")[:,:,0]],[cv2.imread("C:/Users/17324/Downloads/aiFlow/Six.png")[:,:,0]],
[cv2.imread("C:/Users/17324/Downloads/aiFlow/Seven.png")[:,:,0]],[cv2.imread("C:/Users/17324/Downloads/aiFlow/Eight.png")[:,:,0]],
[cv2.imread("C:/Users/17324/Downloads/aiFlow/Nine.png")[:,:,0]],[cv2.imread("C:/Users/17324/Downloads/aiFlow/Ten.png")[:,:,0]],
[cv2.imread("C:/Users/17324/Downloads/aiFlow/Eleven.png")[:,:,0]],[cv2.imread("C:/Users/17324/Downloads/aiFlow/Twelve.png")[:,:,0]],
[cv2.imread("C:/Users/17324/Downloads/aiFlow/Thirteen.png")[:,:,0]],[cv2.imread("C:/Users/17324/Downloads/aiFlow/Fourteen.png")[:,:,0]],
[cv2.imread("C:/Users/17324/Downloads/aiFlow/23.png")[:,:,0]],[cv2.imread("C:/Users/17324/Downloads/aiFlow/57.png")[:,:,0]],
[cv2.imread("C:/Users/17324/Downloads/aiFlow/64.png")[:,:,0]],
[cv2.imread("C:/Users/17324/Downloads/aiFlow/one.png")[:,:,0]]])
Y = np.reshape(Y, (18, 28, 28))
Y = np.reshape(Y, (18, 784))
print(Y)
print(np.shape(Y))
#Y = np.invert(np.array([Y]))
# = np.reshape(Y, (18, 784))
print(Y[1])
Image.fromarray(np.reshape(Y[1], (28, 28))).show()
model = tf.keras.Sequential()
#model.add(tf.keras.layers.Flatten(units = (28, 28)))
model.add(tf.keras.layers.Dense(units = 1))
model.add(tf.keras.layers.Dense(units = 1280, activation = 'sigmoid'))
model.add(tf.keras.layers.Dense(units = 2560, activation = 'relu'))
model.add(tf.keras.layers.Dense(units = 2560, activation = 'relu'))
model.add(tf.keras.layers.Dense(units = 2560, activation = 'relu'))
model.add(tf.keras.layers.Dense(units = 2560, activation = 'relu'))
model.add(tf.keras.layers.Dense(units = 7840, activation = 'relu'))
model.add(tf.keras.layers.Dense(units = 784, activation = 'relu'))
model.compile(optimizer = 'adam', loss = 'categorical_crossentropy', metrics = ['accuracy'])
model.fit(X, Y, epochs = 1000)
img = [[cv2.imread("C:/Users/17324/Downloads/aiFlow/Three.png")[:,:,0]]]
print(np.shape(img))
img = np.reshape(img, (1, 784))
#img = np.reshape(img, (18, 28, 28))
#img = np.reshape(img, (18, 784))
#im = np.reshape(im, (28, 28))
#img.save('my.png')
#print(model.predict([[img]]))
print(model.predict([[0.09]]))
#img.show()
#model.predict(cv2.imread("C:/Users/17324/Downloads/aiFlow/Eight.png"))
Here is what the output looks like.
Epoch 999/1000
1/1 [==============================] - 0s 262ms/step - loss: 1399771.7500 - accuracy: 0.0000e+00
Epoch 1000/1000
1/1 [==============================] - 0s 256ms/step - loss: 1399771.7500 - accuracy: 0.0000e+00
(1, 1, 28, 28)
1/1 [==============================] - 0s 326ms/step
[[199282.06 199288.88 199315.81 199300.83 0. 199299.22
199265.17 199350.97 199292.02 199304.56 199288.55 199294.83
199289.64 199299.23 199297.22 0. 199309.2 199306.39
199298.88 199364.98 199311.77 199319.39 199301.73 199300.73
0. 199309.02 0. 0. 199326.27 199319.03
199299.25 199312. 0. 199290.66 199312.22 0.
0. 199294.34 199302.16 199316.95 199396.31 199282.86
0. 199297.58 199278.92 199348.81 199289.9 199282.81
0. 199356.6 0. 199288.1 199292.84 199300.83
199301.39 199299.83 0. 199278.77 199318.38 199301.17
199326.14 199281.9 0. 199307.53 0. 0.
199331.94 199295.22 199295.66 199253.81 0. 199306.03
199320.08 199302.05 199301.53 199274.25 0. 199289.84
199304.66 199311.42 199294.4 199280.39 0. 199295.4
199288.52 199286.2 0. 0. 190980.31 195136.56
199328.12 199294.19 196189.23 189574.28 185125.86 178575.97
177170.53 177145.08 0. 177149.14 179951.61 190983.16
0. 199294.06 199298.94 199303.94 199271.25 199295.3
199308.17 199301.11 199301.34 199317.2 199316.45 199291.19
199312.8 189280.36 0. 152979.77 153675.66 159425.44
147432.53 143942.23 0. 0. 127356.23 125194.97
128731.125 143976.19 164658.25 0. 185449.77 0.
191019.52 195172.84 199345.67 199319.1 199328.34 199310.11
199326.72 199298.78 199268.34 199284.75 199248.98 188257.53
154988.52 110339.97 108355.984 110099.92 132865.7 123508.63
0. 87205.01 96845.234 91384.75 107316.375 0.
0. 154964.05 130471.39 134176.8 161948.17 166444.45
174034.58 170300.36 181345.98 195137.61 199316.45 199283.16
199313.52 199293.86 199283.97 188174.39 0. 87873.31
89591.49 95854.234 119326.17 101727.664 101038.61 93777.21
0. 0. 110745.26 119310.08 105236.75 0.
102418.36 0. 151198.75 0. 167122.44 166133.92
166776.1 184403.25 0. 0. 199305.39 199359.05
0. 178494.16 0. 0. 75068.34 0.
0. 110044.23 0. 106530.07 89276.71 0.
107541.33 127003.96 107611.13 77874.125 80225.92 80943.51
138736.69 0. 166142.69 166099.33 166120.39 177534.36
199300.33 199299.16 199271.84 199319.77 189268.98 177449.89
0. 111370.75 58839.445 83024.27 104164.52 129708.21
0. 0. 101348.93 0. 107920.38 0.
0. 0. 77496.53 0. 136696.2 184012.34
0. 166099.38 0. 0. 199322.16 199275.78
199289.88 0. 0. 0. 0. 121811.7
72026.87 0. 0. 0. 135331.5 0.
0. 118669.38 121786.58 0. 0. 85833.74
75445.95 99653.39 0. 166042.48 0. 0.
0. 177132.1 199294.84 199243.56 0. 189256.23
188233.28 188241.77 132855.89 0. 95098.125 101292.125
121157.65 0. 0. 113823.55 111694.23 111779.91
0. 141794.56 0. 122496.66 93049.22 99661.66
123181.44 145282.7 158796.56 155006.27 0. 177518.39
199331.9 199326.8 196170.06 0. 0. 188281.98
137700.4 132845.42 111051.555 130080.83 128365.89 143903.88
123481.02 101396.83 117664.79 112747.21 128726.805 118659.72
0. 0. 94017.59 0. 111106.71 128703.734
0. 0. 159493.67 177484.92 199297.69 199319.84
189261.69 188233.02 188230.73 188207.28 146640.47 0.
102352.13 0. 0. 0. 0. 0.
122128.44 0. 0. 126608.17 134312.72 0.
88990.49 0. 0. 115554.06 143876.56 157792.31
166095.27 0. 199305.6 199321.42 188231.62 188229.97
185115.3 179594.12 133575.97 116597.43 91000.64 117601.586
0. 120066.92 102458.055 111036.39 118728.99 124910.44
122199.02 107257.555 117640.99 96140.84 0. 88560.375
0. 121800.93 154977.12 166406.3 172991.95 188579.89
195167.72 199291.38 0. 185075.92 0. 174015.48
0. 112057.375 0. 0. 0. 0.
0. 92730.22 106510.62 0. 119710.516 0.
122145.17 121087.07 0. 106523.766 0. 116679.51
155370.14 166059.9 0. 184054.98 0. 0.
194086.02 178170.9 177151.56 163949.38 0. 0.
79940.23 106829.766 0. 108942.445 0. 94069.695
97273.63 0. 110720.35 110074.805 0. 0.
101049.61 0. 0. 136707.17 155359.36 0.
177152.95 177485.73 192764.16 199298.95 199330.53 177155.78
0. 156036.77 134560.81 0. 83391.04 0.
0. 101715.32 0. 0. 89650.375 111056.54
114484.59 119046.85 121110.24 131135.8 102719.766 106893.805
130792.61 0. 0. 161915.95 188256.89 188248.83
199295.78 199316.97 199290.12 177846.8 0. 155011.12
133207.88 132873.95 106923.89 121442.3 0. 0.
127696.24 0. 98617.73 107628.79 0. 111076.36
122151.36 118343.68 0. 0. 119007.69 0.
151541.23 159865.77 188194.73 188205.42 0. 199295.36
199276.1 188914.53 177163.3 155026.53 132892.56 0.
0. 110665.51 0. 0. 121798.516 115246.49
0. 110733.61 116568.36 0. 119391.94 111033.2
95464.4 94086.45 116641.3 143891.66 144282.92 170555.77
188201.12 192743.14 199276.38 199279.12 199274.8 199303.8
188551.16 166768.1 143942.05 126618.04 86489.24 0.
0. 106557.4 115288. 116584.61 0. 0.
139817.75 144969.05 0. 121783.12 99998.91 103836.14
127651.69 0. 157489.31 181687.67 192741.05 199293.9
199278.8 199320.23 199324.1 199279.97 0. 0.
122143.69 98675.27 86790.7 102431.4 100333.49 93424.05
0. 114570.055 143202.4 0. 138754.5 144661.77
0. 134228.92 0. 0. 143910.22 0.
177145.28 192744.34 199300.58 0. 199296.11 199309.8
199280.16 199333.6 0. 0. 0. 122487.71
104800.29 105194.4 0. 0. 132829.69 144980.12
172970.45 0. 177155.58 174024.9 155692.92 143930.77
143223.83 147744.58 0. 181694.44 192733.56 0.
0. 199292.4 0. 199284.64 0. 199308.11
188904.86 177151.52 0. 155311.94 149808.52 139069.5
0. 143996.98 0. 0. 155029.1 149805.77
0. 157768.78 0. 170618.42 166424.67 177121.16
177169.7 192691.36 199284.88 199332.94 199325.03 199283.77
199290.02 0. 199297.08 199276.08 199280.7 199260.83
183638.55 0. 159523.86 165439.27 160878.25 159532.8
0. 166127.88 166065.23 166092. 0. 155047.64
155034.47 157821.42 0. 181733.8 192740.12 199314.39
199290.89 199343.94 199293.12 0. 199230.34 199275.95
199292.58 199295.38 199331.81 199263.84 199310.98 199292.9
199314.97 199310.86 188835.44 177176.9 171974.3 166116.88
0. 166077.66 0. 0. 166060.02 170609.36
177801.81 199309.22 199271.34 199296.33 199299.78 0.
199285.78 199280.83 199302.1 0. 199310.25 199299.77
199330.94 199344.62 0. 199295.17 199275.64 199313.84
199253.67 199300.25 199304.55 199288.64 199301.17 188884.1
177121.34 177153.11 0. 177132.86 0. 199283.19
199256.03 0. 199317.48 199289.95 199270.36 199283.28
199297.53 0. 0. 199296.03 199302.28 199358.78
199319.67 199310.56 199309.67 199271.89 199297.53 199305.5
199301.12 0. 199309.16 199363.48 199308.92 199300.34
199272.8 0. 199269.58 199265.88 199278.77 199324.14
0. 199297.64 199331.98 199325.75 0. 199324.12
199294.81 199289.08 199270.95 199322.05 199295.14 0.
199300.19 199258.08 199314.14 199310.08 199315.92 0.
199299.31 199298.56 199375.52 199290.88 199288.38 199311.53
199289.39 199322.83 199302.05 199373.31 199284.28 199314.86
199288.2 199317.53 199305.3 199313.55 ]]
Notice how the accuracy is really low. The network is also outputting numbers waaaaaay above 255. Even when I switch the labels and use a sigmoid, it deosnt' work.
Please note that I have tried playing around with the loss and optimizer. These combinations were the ones that I could get the most out of, not that they actually produced something worthwhile.

Through testing, here is what I have found. Basically, we need to use mse and train over 2000 epochs. This was found through testing different scaling of the data. The data doesn't need to be scaled.

Related

checking multiplication table arrays

My code keeps returning false what am I doing wrong? This is the feedback I am getting.
checkTable() should only return false when it finds an incorrect entry.
Failed: java.lang.AssertionError: checkTable() should return false when entry at index 0 is not equal to 0.
/**
* This method checks if an array of ints contains a correctly calculated
* multiplication table.<br/>
* Precondition: multTable IS NOT null. (PRECONDITIONS SPECIFY RESPONSIBILITIES
* ON A METHOD'S CALLER; YOU SHOULD ASSUME THIS IS TRUE.)
*
* #param constant
* Value used to check the multiplication table.
* #param multTable
* Table to be checked.
* #return True if every entry in the array stores the value of {#code constant}
* * the index for that entry; or false if at least one entry is
* incorrect.
*/
public static boolean checkTable(int constant, int[] multTable) {
int i=0;
for(i=0;i<multTable.length;i++){
int mult = constant*i;
if(mult==multTable[i]) {
return true;
}
}
return false;
}
Right now you are immediately returning true if only one entry in the Array is valid:
if(mult==multTable[i]) {
return true;
}
It needs to be the other way around:
for(i=0;i<multTable.length;i++){
int mult = constant*i;
if(mult!=multTable[i]) {
return false;
}
}
return true;
Just step through the code, line by line. Let's say the constant is '5', and the input is new int[] {0, 15, 38}; which is clearly not a multiplication table.
int i = 0;: i now exists. The value of i is now 0.
for (int i = 0; i < multTable.length; i++) { we're going to loop 3 times. We enter the loop with the first value (0).
int mult = constant * i;: mult now exists. The value of mult is 0 (because 5*0 is 0).
if (mult == multTable[i]) return true;: mult is 0; the first item in our example multTable input is 0. Therefore the if triggers and the entire method returns, with value true. The remaining elements aren't checked at all.
The fix is obviously NOT to return when the first element is correct. When you hit a 'mistake' you know immediately that the answer to the question "Is this a valid multiplication table" is false. But when you hit a correct entry that doesn't mean you know the answer. You'd have to keep going.
This smells of homework so I'll let you do the honours of figuring out what that means and how you can fix your code.
NB: This is how you solve problems with code: You reason through it. You check what the code actually does (using a debugger, or if that's a bridge too far to learn for now, add a lot of System.out.println statements). The point where your code doesn't match what you thought it should do is the point where you figured out the bug.

Java Recursive Method how does it work?

I'm relatively new to Java programming and I've just started learning recursion, but I can't seem to figure out how this method works in my head.
private static int mystery(int w) {
{
if (w < 0) return 0;
int x = mystery (w-2);
return w - x;
}
}
Whenever a variable like 100 is put in, it outputs 50. When 200 is input, it outputs 100. When 2 is input, it outputs 2. When 25 is input, 13 is output. I'm not sure how this method works, and I'm trying to wrap my head around it.
The way I currently view it, if you put in 100, it'll bypass the first return statement since it is greater than 0.
when it gets to the second line, it'll do 100-2, which brings in 98, then goes to the third line and does 100 - 98 = 2. Which is then returned to the original call.
I know I'm messing up on the second line of the method where the mystery (w-2) is. I assume it would bring back the result of w-2 to the beginning of the method again, and it would continue to do the method over and over again until w is smaller than 0, which should output 0 again regardless of the answer. But that's not what happens, and I don't know why.
Can anyone explain what is going on here?
What you are missing is that on the second line it doesn't just do w - 2, but calls itself with w - 2. It doesn't go further until the call returns. And the second call calls itself if w isn't < 0 and so on until you reach value lower than 0 and then return. The execution will go like this, if you visualize it:
mystery(10)
> skip first line
> x = mystery(8)
> skip first line
> x = mystery(6)
> skip first line
> x = mystery(4)
> skip first line
> x = mystery(2)
> skip first line
> x = mystery(0)
> skip first line
> x = mystery(-2)
> return 0
> return 0 - 0 (0)
> return 2 - 0 (2)
> return 4 - 2 (2)
> return 6 - 2 (4)
> return 8 - 4 (4)
> return 10 - 4 (6)
With example of w = 10. I hope you understand it better now.
private static int mystery(int w) {
{
if (w < 0) return 0;
int x = mystery (w-2);
return w - x;
}
}
Let's imagine that we call mystery(3). What happens? w<0) is false, so we don't return 0. In the next line, we call some function called mystery using the value 3-2=1 as its argument.
Despite the fact that this function we've called happens to be the same one we've just called, it's still an ordinary function call, and it returns a value. It does this by calling the function called mystery, this time using the value -1 as the argument. And this time w<0 is true, so we just return 0. Now we're back in the second call to mystery, and we've set x = 0. So that call returns w - 0 = 1. That puts us back in the first call, and now x = 1, so we return w-x = 3-1 = 2.
You might want to take a few minutes and work through this using w=4 and see what you get - this will help you understand how the recursive calls work.
After you've done this, I suggest you add a print statement or two in the function to tell you where you are and what's happening, and that'll also help - but do it on paper first.
The two given answers are excellent. Both focus on the way how to get a grasp of what recursion is. The problem with recursion is, that it is so unnatural to one who do not know what recursion is, or do not know someone who does. It's like a snake eating itself again and again.
The best way to understand recursion is to write down the calls to a recursive method, by noying the current state when it's called, and after the call write the result back. You stack up the calls and that's also the way to not used recursion at all.
So do not try too hard to understand recursion at first but first focus on the program flow. If you have seen enough recursions, it will come to you.

0.%d range between 0-100 is the same as 100-1000

I have the command:
string.format("movel(p[0.%d,- 0.%d, 0.%d, -0.5121, -3.08, 0.0005])"+ "\n", averageX1, averageY1, averageY2 )
Where average value can change from 0 to 700. When the value is
averageX1 = 344
averageY1 = 222
averageY2 = 150
The command becomes:
movel(p[0.344,- 0.222, 0150, -0.5121, -3.08, 0.0005])
When one of the average becomes lower then 100:
averageX1 = 80
The command becomes
movel(p[0.**80**,- 0.222, 0150, -0.5121, -3.08, 0.0005])
I want it to become :
movel(p[0.**080**,- 0.222, 0150, -0.5121, -3.08, 0.0005]
How can I change this so it will have the value that can be from 0 tot 100.
ps. It is the "0" that must be in front of the "8".
kind regards
pascal
Change 0.%d to 0.%03d. Also see here.

Index out of bounds exception in homework

I'm trying to do a homework assignment. I have to use dynamic programming to display whether the next person to move is in a win/loss state. I don't need help with the actual problem, I need help with an index out of bounds exception I'm getting that baffles me. I'm only going to paste part of my code here, because I only need the for loops looked at. I also don't want anyone in my class seeing all my code and copying it. If you need more data please let me know. So here is the code:
if(primeArray[x] == true){
for(int i = 1; i <= x; i++){
if(primeArray[i]== true){
newRowNumber = x - i;
}
if(dynaProgram[newRowNumber][columnNumber] < minimum){
minimum = dynaProgram[newRowNumber][columnNumber];
}
}
}
//COMPOSITE CASE FOR X!
else{
for(int k = 1; k <= x; k++){
if((primeArray[k] == false)){
newRowNumber = x - k;
}
if(dynaProgram[newRowNumber][columnNumber] < minimum){
minimum = dynaProgram[newRowNumber][columnNumber];
}
}
For some reason the if(primeArray[i] == true runs correctly, but I'm getting index out of bounds exception on if(primeArray[k] == false. The only difference between these two is the use of the variable k over i in the for loop.(the for loops are identical) I haven't used either variables anywhere else in my code. I have no idea why this occurs for one but not the other. In both cases, x remains the same number.
I am also getting an index out of bounds exception on the second minimum = dynaProgram[newRowNumber][columnNumber], while the first doesn't encounter an error. I know it's probably a stupid error, but I can't figure it out. If I change the 'k' for loop to k < x the index of out bounds exception in the if(primeArray[k] == false line goes away, but then it isn't correct. (The error on the second minimum = dynaProgram[newRowNumber][columnNumber] doesn't go away however.)
All this code is in a nested for loop which iterates through the rows and columns in the table to fill them in. If I remove the above code and just put dynaProgram[rowNumber][columnNumber] = 1 I don't have an issue, so I don't believe that is the problem.
When accessing an array of length 5 (for example)
int[] fred = new int[5];
the first element will be fred[0] and the last will be fred[4]
So when doing something like:
if(primeArray[i]== true){
Make sure that i is less than the array length. Using a value of i equal to the array length will throw an exception.

Solving maze using stacks

I been working on this code for a while and can't seem to get it to work. I have started over multiple times. I am not sure if my logic is off or if I could be doing something better. Any suggestion in the right direction or new ideas to try would be helpful. I understand that a maze could be solved recursively but for this part of the assignment I need to use a stack.
I created two stacks. One for the path the other for spots I already searched. Ideally I would check to see if the searched path contains the next spot in a direction. If it does it checks another direction.
Sample maze
0 1 0 1 0
0 0 0 1 0
0 1 0 0 0
0 1 0 1 1
0 1 0 0 0
My algorithm seems to get stuck between 2,3 and 2,4. Never explores 1,4 or 0,4. I see it keep bouncing between 2,3 and 2,4 in an infinite loop. So it seems my searched.contains() is not functioning properly. Any suggestion to fix my searched stack? Ideally, when I run my code. I want it to check East, South, west then North has already been searched or not. If all points have been checked it will pop the last position from my path stack using current= path.pop inside the while loop and repeat.
Position is a custom class. I have considered adding a previous position variable to the constructor in the position class but seems to not to be needed if I can get my path stack to work. If I am wrong on this please let me know.
public static Position [] stackSearch(char [] [] maze){
//todo: your path finding algorithm here using the stack to manage search list
//your algorithm should modify maze to mark positions on the path, and also
//return array of Position objects coressponding to path, or null if no path found
ArrayDeque <Position> path = new ArrayDeque<Position>();
ArrayDeque <Position> searched = new ArrayDeque<Position>();
//creates position object
Position start = new Position(0,0,'0');
Position current;
Position north,south, east, west;
int i = 0; int j = 0;
//push (0,0) onto stack
path.push(start);
searched.push(start);
while(!path.isEmpty()){
current=path.pop();
i=current.i;
j=current.j;
if(i==maze.length-1 && j==maze.length-1 && maze[i][j]=='0'){
Position[] trail= new Position [path.size()];
while(!path.isEmpty()){
for(int k=0; k<path.size();k++){
trail[k]=path.pop();
}
return trail;
}
}
System.out.println(i +"," +j);
//check east.
east= new Position(i,j+1,'0');
south= new Position(i+1,j,'0');
west= new Position(i,j-1,'0');
north= new Position(i-1,j,'0');
if (j+1 >= 0 && j+1 < maze.length && maze[i][j+1] == '0' && searched.contains(east)==false)
{
searched.push(east);
path.push(current);
path.push(east);
}
//check south, add its position to the list.
else if (i+1 >= 0 && i+1 < maze.length && maze[i+1][j] == '0' && searched.contains(south)==false)
{
searched.push(south);
path.push(current);
path.push(south);
}
//check west.
else if (j-1 >= 0 && j-1 < maze.length && maze[i][j-1] == '0' && searched.contains(west)==false)
{
searched.push(west);
path.push(current);
path.push(west);
}
//check north
else if (i-1 >= 0 && i-1 < maze.length && maze[i-1][j] == '0' && searched.contains(north)==false)
{
searched.push(north);
path.push(current);
path.push(north);
}
}
return null;
}
I would guess that the problem lies, not in the code you posted, but rather in the Position class. If you have not overridden hashcode() and equals() in the Position class, the contains() comparison here will be looking for object equality.
So when you ask if searched.contains(east), having just created east as a new object, it will return false, even though east's coordinates perfectly match what is already in your search.
See this answer for more.
A common solution to solving a maze is BFS, which is both optimal and complete [it always find a solution if there is one, and also it finds the shortest one].
Using a stack, is actually simulating a DFS, which is not optimal.
About the specific problem, where contains() doesn't do its job, it will be hard to know what the problem is without the source for the class Position, but a possible reason is you did not override equals(), so the default equals() is still checking for identity, and not equality - which is obviously not true.

Categories