Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
20 commits
Select commit Hold shift + click to select a range
91e7c70
added sloane.txt
sloanerudometkin Jul 10, 2026
6ed09a6
remove sloane.txt
sloanerudometkin Jul 10, 2026
735e346
update read me
sloanerudometkin Jul 10, 2026
6a11555
added some operations
sloanerudometkin Jul 11, 2026
07b8334
added getOneNumber and square root function so far
sloanerudometkin Jul 11, 2026
d1d25d7
removed an error
sloanerudometkin Jul 11, 2026
6ce16b7
removed another error
sloanerudometkin Jul 11, 2026
3094743
added state to calculator.py - ljd 7/11/26
LDurham1213 Jul 11, 2026
3deca9e
Add status and test file 7/11/26 - LJD
LDurham1213 Jul 11, 2026
90ee18b
Merge remote-tracking branch 'origin/Sloane' into final-calculator
LDurham1213 Jul 11, 2026
2698343
restore calculator functionality and custom feature - LJD 7:54PM 7/12/26
LDurham1213 Jul 12, 2026
1befc16
Integrate calculator, scientific, mem and custom features - LJD 8:40P…
LDurham1213 Jul 13, 2026
cac64ca
Update README with completed calculator features LJD - 7/12/26 9:56PM
LDurham1213 Jul 13, 2026
11eb231
Add unit tests for calculator and scientific calculators LJD 7/12/26 …
LDurham1213 Jul 13, 2026
2c6b818
Final project submission - LJD SR 7/12/26 10:48PM
LDurham1213 Jul 13, 2026
30f463c
Final Calculator for IBM - ljd sr 7/13/26 8:01a
LDurham1213 Jul 13, 2026
ec1052e
Update test doc - ljd 7/13/26 11:58
LDurham1213 Jul 13, 2026
634e919
start of code for gui calc
LDurham1213 Jul 13, 2026
d262e00
added numbers to the menu 7-13-26 LJD
LDurham1213 Jul 13, 2026
145f5b2
fixed typo for memory store ljd 7-13-26
LDurham1213 Jul 13, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 18 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -66,9 +66,25 @@
- Ln (natural logarithm)
- e<sup>x</sup> (inverse natural logarithm)

### Custom Features
- Tip Calculator
allows users to calculate the total cost of a bill including gratuity.

- Temperature Converter
allows users to convert temperatures between Celsius and Fahrenheit.

### Custom Features
These custom features were selected bec they demonstrate the ability to extend the calculator beyond standard mathematical operations while applying real-world problem-solving. The Tip Calculator provides a practical financial calculation, while the Temperature Converter demonstrates the implementation of mathematical formulas and conditional logic.

### User-Friendly Menu System
-The app provides an interactive menu that displays all available calculator operations. Users can simply enter the name of the desired operation rather than remembering commands. The menu also includes a HELP option to redisplay all available commands at any time, making the calculator easier to navigate and use.

### Error Handling
-The calculator validates user input and displays meaningful error messages for invalid operations, including:
- Invalid numeric input
- Division by zero
- Invalid exponent operations
- Invalid mathematical operations
-The calculator prevents additional operations while an error is displayed until the user clears the error, ensuring consistent and predicatable behavior.

In addition to the Core and Scientific features, you are required to create at least two of your own features for the calculator. They can be any two features that are not already covered and that you can implement as you see fit. These features must be properly tested.

Expand All @@ -91,3 +107,4 @@ The following functions should take the displayed value (x) and updated it accor
## Submission

Completed projects should be submitted by submitting a pull request against the [original repository](https://git.zipcode.rocks/Cohort4.2/ZCW-MacroLabs-OOP-ScientificCalculator). All work should be done in your own repository.

25 changes: 0 additions & 25 deletions calctests.py

This file was deleted.

308 changes: 303 additions & 5 deletions calculator.py
Original file line number Diff line number Diff line change
@@ -1,12 +1,310 @@
class Calculator:

# Error Messages
INVALID_INPUT_ERROR = "Invalid input"
DIVIDE_BY_ZERO_ERROR = "Cannot divide by zero"
OVERFLOW_ERROR = "Number too large"
INVALID_EXPONENT_ERROR = "Invalid exponent"
INVALID_OPERATION_ERROR = "Invalid operation"
## ERROR = "Err"-------

#status set here
def __init__(self):
pass
self.display: int | float = 0
self.error: str | None = None
self.memory: int | float = 0
self.trig_mode: str = "Radians"

#----------------
#Display methods
#----------------
def getDisplay(self):
"""
Return the error message when an error exists.
Otherwise, return the current numeric display.
"""
if self.hasError():
return self.error

return self.display

def hasError(self):
"""
Return True when an error message has been stored.
"""
return self.error is not None

def clear(self):
"""
Reset both the display and the error status.
"""
self.display = 0
self.error = None
return self.display

def setDisplay(self, value):
"""
Set the calculator display to a valid number.
The calculator must be cleared before continuing
after an error.
"""
if self.hasError():
return self.error

if not self.isValidNumber(value):
self.error = self.INVALID_INPUT_ERROR
return self.error

self.display = value
return self.display

def isValidNumber(self, value):
"""
Boolean values are excluded bc Python treats T / F as int
"""

return(
isinstance(value, (int, float))
and not isinstance(value, bool)
)
#---------------
#Memory methods
#---------------
def memory_add(self): #M+
"""
Add the current display value to memory.
Update both memory and the display.
"""
if self.hasError():
return self.error

# if not self.isValidNumber(self.display):
# self.error = self.INVALID_INPUT_ERROR
# return self.error

self.memory += self.display
self.display = self.memory
return self.display

def memory_clear(self): #MC
"""
Reset memory to zero.
Leave the current display unchanged.
"""

if self.hasError():
return self.error

self.memory = 0
return self.display

def memory_recall(self): # MRC
"""
Copy the stored memory value to the display.
"""
if self.hasError():
return self.error

self.display = self.memory

return self.display

def memory_store(self):
"""
Store the current display value in memory.
Leave the display unchanged.
"""
if self.hasError():
return self.error

if not self.isValidNumber(self.display):
self.error = self.INVALID_INPUT_ERROR
return self.error

self.memory = self.display
return self.display

#---------------
#Simple math functions
#---------------
def add(self, x, y):
return x + y
if self.hasError():
return self.error

if not self.isValidNumber(x) or not self.isValidNumber(y):
self.error = self.INVALID_INPUT_ERROR
return self.error
try:
self.display = x + y
except OverflowError:
self.error = self.OVERFLOW_ERROR

return self.getDisplay()

def subtract(self, x, y):
if self.hasError():
return self.error

if not self.isValidNumber(x) or not self.isValidNumber(y):
self.error = self.INVALID_INPUT_ERROR
return self.error

try:
self.display = x - y
except OverflowError:
self.error = self.OVERFLOW_ERROR

return self.getDisplay()

def multiply(self, x, y):
if self.hasError():
return self.error

if not self.isValidNumber(x) or not self.isValidNumber(y):
self.error = self.INVALID_INPUT_ERROR
return self.error

try:
self.display = x * y
except OverflowError:
self.error = self.OVERFLOW_ERROR

return self.getDisplay()

def divide(self, x, y):
if self.hasError():
return self.error

if not self.isValidNumber(x) or not self.isValidNumber(y):
self.error = self.INVALID_INPUT_ERROR
return self.error

if y == 0:
self.error = self.DIVIDE_BY_ZERO_ERROR
return self.error

try:
self.display = x / y
except OverflowError:
self.error = self.OVERFLOW_ERROR

return self.getDisplay()

def inverse(self):
if self.hasError():
return self.error

if not self.isValidNumber(self.display):
self.error = self.INVALID_INPUT_ERROR
return self.error

if self.display == 0:
self.error = self.DIVIDE_BY_ZERO_ERROR
return self.error

try:
# ensure numeric division even if display is a numeric string; will raise on invalid types
self.display = 1 / float(self.display)
except OverflowError:
self.error = self.OVERFLOW_ERROR

return self.getDisplay()

def exponentiate(self, exponent):
if self.hasError():
return self.error

if not self.isValidNumber(self.display):
self.error = self.INVALID_INPUT_ERROR
return self.error

if not self.isValidNumber(exponent):
self.error = self.INVALID_INPUT_ERROR
return self.error

try:
result = self.display ** exponent

if isinstance(result, complex):
self.error = self.INVALID_EXPONENT_ERROR
else:
self.display = result

except ZeroDivisionError:
self.error = self.DIVIDE_BY_ZERO_ERROR
except OverflowError:
self.error = self.OVERFLOW_ERROR
except (TypeError, ValueError):
self.error = self.INVALID_EXPONENT_ERROR

return self.getDisplay()

def switch_sign(self):
if self.hasError():
return self.error

if not self.isValidNumber(self.display):
self.error = self.INVALID_INPUT_ERROR
return self.error

self.display = -self.display
return self.display

# added Sloanes code 7/12/26 8:07p
def square(self, x):
if self.hasError():
return self.display

if not self.isValidNumber(x):
self.error = self.INVALID_INPUT_ERROR
return self.error

try:
self.display = x ** 2
except OverflowError:
self.error = self.OVERFLOW_ERROR
return self.getDisplay()

def squareroot(self, x):
if self.hasError():
return self.error

if not self.isValidNumber(x):
self.error = self.INVALID_INPUT_ERROR
return self.error

if x < 0:
self.error = "Cannot calculate the square root of a negative number"
return self.error

try:
self.display = x ** 0.5
except OverflowError:
self.error = self.OVERFLOW_ERROR
return self.getDisplay()

def sub(self, x, y):
return 0

#---------------
# Utility functions
#---------------
def absolute_value(self):
if self.hasError():
return self.error

if not self.isValidNumber(self.display):
self.error = self.INVALID_INPUT_ERROR
return self.error

self.display = abs(self.display)
return self.display

def percentage(self):
if self.hasError():
return self.error

if not self.isValidNumber(self.display):
self.error = self.INVALID_INPUT_ERROR
return self.error

# add lots more methods to this calculator class.
self.display = self.display / 100
return self.display
Loading