I've been doing this programming challenge all day, and I've finished up a python program that, to me, should logically work and output the correct answer- but it does not. I have a program from a friend that outputs the correct answer, so I have a way to compare my output to theirs but I see no reason why mine should not be outputting the correct answer also.
The challenge is to obtain a passcode from the pixels in an image, which are numbered 0..99 for the first row, 100..199 for the second row etc. The white pixels represent ascii codes. The ascii code for a particular white pixel is equal to the offset from the last white pixel. For example, the first white pixel of an image at location 65 would represent ascii code 65 ('A'), and the next at location 131 would represent ascii code (131 - 65) = 66 ('B') and so on.
The image used in both programs for the challenge
Here is my code (incorrect ouput, Python 3):
import cv2
import numpy as np
# load img
im = cv2.imread('PNG.png')
# define colour
white = [255,255,255]
# get coords
Y,X = np.where(np.all(im==white,axis=2))
a = X.tolist()
# format list to string
x = str(a)
# clean string
x = x.replace(' ', '',)
x = x.replace('[', '')
x = x.replace(']', '')
# reformat CSV string to list
x = x.split(",")
# map each str to int
x = map(int, x)
# convert mapped outputs to list of ints
x = list(x)
firstX = x[0]
print()
print()
print('og list: ',x)
print()
print()
y = list(x)
y.pop(0)
y.insert(len(y),00)
print('conv list: ',y)
print()
print()
length = len(x)
repeatTime = 0
z = []
while repeatTime < 40:
outputInt = (y[0] - x[0])
z.insert(len(z),outputInt)
y.pop(0)
x.pop(0)
repeatTime = 1
z.insert(0,firstX)
print(z)
# Remove Negative Elements in List
# Using list comprehension
r = [ele for ele in z if ele > 0]
print()
print()
# printing result
print("List after filtering : " str(r))
print()
print()
print(r)
print()
print()
v = (''.join(chr(i) for i in r))
print(v)
CODE = {'A': '.-', 'B': '-...', 'C': '-.-.',
'D': '-..', 'E': '.', 'F': '..-.',
'G': '--.', 'H': '....', 'I': '..',
'J': '.---', 'K': '-.-', 'L': '.-..',
'M': '--', 'N': '-.', 'O': '---',
'P': '.--.', 'Q': '--.-', 'R': '.-.',
'S': '...', 'T': '-', 'U': '..-',
'V': '...-', 'W': '.--', 'X': '-..-',
'Y': '-.--', 'Z': '--..',
'0': '-----', '1': '.----', '2': '..---',
'3': '...--', '4': '....-', '5': '.....',
'6': '-....', '7': '--...', '8': '---..',
'9': '----.'
}
CODE_REVERSED = {value:key for key,value in CODE.items()}
def from_morse(s):
return ''.join(CODE_REVERSED.get(i) for i in s.split())
print(from_morse(v))
My output:
----.. - -..-- .....--.
-invalid morse code-
Here is my friend's code (correct output, Python 2.7)
from PIL import Image
img_file = Image.open("PNG.png")
img_width, img_height = img_file.size
img_pixel = img_file.load()
preposition=0
morse_code=""
answer=""
char_morse_dict={
'A':'.-','B':'-...','C':'-.-.','D':'-..','E':'.','F':'..-.',
'G':'--.','H':'....','I':'..','J':'.---','K':'-.-','L':'.-..',
'M':'--','N':'-.','O':'---','P':'.--.','Q':'--.-','R':'.-.',
'S':'...','T':'-','U':'..-','V':'...-','W':'.--','X':'-..-',
'Y':'-.--','Z':'--..','0':'-----','1':'.----','2':'..---','3':'...--',
'4':'....-','5':'.....','6':'-....','7':'--...','8':'---..','9':'----.',
'.':'.-.-.-',',':'--..--','?':'..--..',"'":'.----.','/':'-..-.','(':'-.--.-',
')':'-.--.-',':':'---...',';':'-.-.-.','=':'-...-',' ':'.-.-.','-':'-....-',
'_':'..--.-','"':'.-..-.','$':'...-..-','':''
}
# fetch ASCII code from image
for y_point in range(img_height) :
for x_point in range(img_width) :
if img_pixel[x_point, y_point] == 1 :
# convert ASCII code to "dits" and "dahs" in morse code
symbol = chr(x_point 100 * y_point - preposition)
if symbol != ' ' :
morse_code = symbol
else :
# decode morse code to character
char = [key for key, value in char_morse_dict.items() if value == morse_code][0]
answer = char
morse_code = ""
preposition=x_point 100 * y_point
# bye bye
print(answer)
His output:
--.- --... .-. --... --- ..... .-. --... ..- ..-
Q7R7O5R7UU
I have looked through mine for hours and can not for the life of me figure out what is going wrong. I know something occurs during the part of the code where the pixel position values are converted to morse, but I can't see what exactly the issue happens to be.
If somebody could please help me point out what is going wrong so that I may adapt my code and learn from my mistake in the hopes my skills improve, I would be extremely thankful.
CodePudding user response:
You calculate:
Y,X = np.where(np.all(im==white,axis=2))
but you never use Y
, only X
so you are effectively ignoring which row each pixel is in. If a pixel is at row Y, column X, you should assign its position like this:
offset = (Y * imageWidth) X
CodePudding user response:
If I understand correctly what you want to do, it is to find the offset for every white pixel in the image, and then calculate the difference between them.
This can be done succinctly using np.diff
with the prepend
argument. Note that to calculate the offset, you need to multiply y
by the width of the image.
import numpy as np
def decode_message(image):
_, width, _ = im.shape
y, x = np.where(np.all(image == 255, axis=2))
offsets_from_start = width * y x
differences = np.diff(offsets_from_start, prepend=[0])
return ''.join(chr(d) for d in differences)