Skip to content

Instantly share code, notes, and snippets.

@dannytranlx
Last active December 26, 2015 16:09
Show Gist options
  • Save dannytranlx/7177304 to your computer and use it in GitHub Desktop.
Save dannytranlx/7177304 to your computer and use it in GitHub Desktop.
One of my submissions to a challenge of IEEEXtreme 7.0

Acadox challenge

Acadox vision is to provide innovative and modern Learning Management technologies that empowers the faculty and students to engage and collaborate in a simple and efficient manner.

One of the professor, who loves Acadox so much, posted on his page as a teaser problem for his students to prepare for their programming exam. The problem posted was as follows:

Develop program that emulates a simple hexadecimal calculator that uses postfix notation. Perform the operations of addition, subtraction, logical and, logical or, logical not, and logical exclusive or.

Description

Since Acadox is social environment for learning. The professor posted the following description on his page: The programmer’s calculator accepts a string of hexadecimal digits and operators in reverse Polish (postfix) notation then produces the result. Input digits represent 16 bit unsigned binary bit strings.

Input

The program must accept a sequence of operators and hexadecimal digits following the postfix form, as follows. Digits: Leading zeros are optional, alphas are not case sensitive: {[0-9 | A-F | a-f]}1-4

Each input item is delimited by a white space. An input stream is terminated with a new-line. No more than 20 items are accepted.

Output

The program must display the result of evaluating the entire postfix expression as single hexadecimal string, with leading zeros and upper case letters. If any input is invalid, the string “ERROR” is displayed.

All operations are bitwise – there is no representation of negative quantities. An overflow: x + y > FFFF results in FFFF. An underflow, x – y < 0000, results in 0000.

Sample Input 1:

1 1 +

Sample Output 1:

0002

Sample Input 2:

F 1 -

Sample Output 2:

000E

Sample Input 3:

F - 1

Sample Output 3:

ERROR

import sys
class CalcException(Exception):
pass
def _plus(value_1, value_2):
return value_1 + value_2
def _sub(value_1, value_2):
if(value_1 > value_2):
return value_1 - value_2
return 0
def _and(value_1, value_2):
return value_1 & value_2
def _or(value_1, value_2):
return value_1 | value_2
def _not(value_1):
result = ""
s_bin = bin(value_1)
string = str(s_bin)
for bit in string[2:].rjust(16, '0'):
if bit == "1":
result += "0"
else:
result += "1"
return int(result, 2)
def _xor(value_1, value_2):
return value_1 ^ value_2
def is_number(s):
try:
int(s, 16)
return True
except ValueError:
return False
try:
# get input
input = sys.stdin.read()
arrInput = input.split(" ")
# init operations
operations = { '+' : _plus,
'-' : _sub,
'&' : _and,
'|' : _or,
'~' : _not,
'X' : _xor,
'x' : _xor
}
# call operation
total = []
if len(arrInput) == 1 or len(arrInput) >= 20:
raise CalcException
for i, value in enumerate(arrInput):
if is_number(value) and int(value, 16) <= 65535: # if current is number
total += [int(value, 16)]
else: # if current not number (aka is operator)
# do operation
if value in operations:
if value == '~' and len(total) >= 1:
value_1 = total.pop(0)
total += [operations[value](value_1)]
elif len(total) >= 2:
value_1 = total.pop(0) # get top
value_2 = total.pop(0) # get 'new' top
total += [operations[value](value_1, value_2)]
else:
raise CalcException
else:
raise CalcException
if len(total) > 1 or len(total) == 0:
raise CalcException
if total[0] > 65535:
total[0] = 65535
elif total[0] < 0:
total[0] = 0
sys.stdout.write(str(hex(total.pop()))[2:].rjust(4, '0').upper())
except CalcException:
sys.stdout.write('ERROR')
Problem Author: IEEE
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment