ENGR 103: Engineering Computation & Algorithmic Thinking | Dr. Cheng Li | Oregon State University
A programming midterm tests whether you can read, trace, and write code by hand — without an IDE to autocomplete or highlight errors for you. Here's how to build those skills before exam day.
for or while loop and write a table of variable values at every iteration. If you can't trace it, you don't understand it.+= to +, then explain why it breaks. Debug drills build the same skill tested on "find the error" questions.You are allowed one 8.5×11 handwritten notes page (double-sided). Use it strategically — don't copy slides verbatim.
while loop skeleton is worth more than three specific examples. Write the skeleton; you can fill in any specific problem from it.if, elif, else, for, whilef'{x:.4f}', f'{x:>8}', f'{x:.2e}'// vs / vs %print syntax, don't write it down.| Type | Example | Notes |
|---|---|---|
int | x = 7 | Whole numbers, positive or negative |
float | x = 3.14 | Decimal numbers; stored in binary (not exact) |
str | x = 'hello' | Sequence of characters; immutable |
bool | x = True | Only True or False (capital T/F) |
| Operator | Meaning | Example → Result |
|---|---|---|
+ | Addition / string concat | 3 + 4 → 7 | 'a' + 'b' → 'ab' |
** | Exponentiation | 2 ** 8 → 256 |
/ | Float division (always float) | 7 / 2 → 3.5 |
// | Integer (floor) division | 7 // 2 → 3 |
% | Modulo (remainder) | 7 % 2 → 1 |
int(3.9) # → 3 (truncates, does NOT round)
int('42') # → 42
float(5) # → 5.0
str(3.14) # → '3.14'
type(3.14) # → <class 'float'>
int(3.9) gives 3, not 4. Python truncates toward zero, it does not round.
A variable is a name bound to an object. Reassigning creates a new binding — it does not change the original object.
x = 5 # x is bound to the integer 5
x = x + 1 # x is now bound to 6; the 5 object is unchanged
y = x # y and x both point to 6
x = 0 # x now points to 0; y is still 6
s = 'Python'
s[0] # 'P' (first character, index 0)
s[-1] # 'n' (last character)
s[1:4] # 'yth' (index 1 up to but NOT including 4)
s[:3] # 'Pyt' (from start up to index 3)
s[3:] # 'hon' (from index 3 to end)
len(s) # 6
| Method | Example → Result |
|---|---|
s.upper() | 'hello'.upper() → 'HELLO' |
s.lower() | 'HI'.lower() → 'hi' |
s.strip() | ' hi '.strip() → 'hi' |
s.replace(a,b) | 'cat'.replace('c','b') → 'bat' |
name = input('Enter your name: ') # always returns a string
age = int(input('Enter your age: ')) # convert if you need a number
print('Hello,', name) # comma adds a space
print(f'You are {age} years old.') # f-string
x = 3.14159
print(f'{x:.2f}') # → 3.14 (2 decimal places)
print(f'{x:.4f}') # → 3.1416
print(f'{x:8.3f}') # → 3.142 (8 wide, 3 dp, right-aligned)
print(f'{x:.2e}') # → 3.14e+00 (scientific notation)
n = 42
print(f'{n:05d}') # → 00042 (zero-padded, width 5)
score = 85
if score >= 90:
print('A')
elif score >= 80:
print('B')
elif score >= 70:
print('C')
else:
print('Below C')
# Compound conditions
if score >= 70 and score < 90:
print('Passing but not excellent')
elif and else are only reached if all earlier conditions were False. Order matters — Python evaluates top to bottom and stops at the first True.
for i in range(5): # 0, 1, 2, 3, 4
print(i)
for i in range(2, 10, 3): # 2, 5, 8 (start, stop, step)
print(i)
for i in range(10, 0, -2): # 10, 8, 6, 4, 2 (counting down)
print(i)
range(start, stop, step) includes start but never includes stop.
# Generic pattern
variable = initial_value
while condition_using_variable:
# do something
variable = updated_value # MUST change variable or loop runs forever
# Example: sum 1 + 2 + 3 + ... until sum exceeds 20
total = 0
n = 1
while total <= 20:
total += n
n += 1
print(total, n)
# break: exit the loop immediately
for i in range(10):
if i == 5:
break # stops at 5; never prints 5, 6, 7, 8, 9
print(i)
# continue: skip the rest of this iteration
for i in range(8):
if i % 2 == 0:
continue # skip even numbers
print(i) # prints 1, 3, 5, 7
For the loop below, trace every iteration:
x = 1
count = 0
while x < 50:
x = x * 3
count += 1
x = 81, count = 4.
Try every integer candidate until you find the answer or prove it doesn't exist.
# Find the integer cube root of a perfect cube
target = 27
guess = 0
while guess ** 3 < target:
guess += 1
if guess ** 3 == target:
print(f'Cube root of {target} is {guess}')
else:
print(f'{target} is not a perfect cube')
candidate**n >= target, then check for exact match. This only finds perfect integer roots — for non-perfect values, use approximation (Week 5).
Every integer can be expressed as a sum of powers of 2. Python converts automatically; understanding the concept matters for interpreting float precision limits.
| Decimal | Binary | Powers of 2 |
|---|---|---|
| 5 | 101 | 2² + 2⁰ = 4 + 1 |
| 13 | 1101 | 2³ + 2² + 2⁰ = 8 + 4 + 1 |
| 16 | 10000 | 2⁴ |
# Accumulate a running sum
total = 0
for i in range(1, 11): # 1 through 10
total += i
print(total) # 55
# Count how many values satisfy a condition
count = 0
for i in range(1, 101):
if i % 7 == 0: # divisible by 7
count += 1
print(count) # 14
Instead of checking every integer, step through small increments until |guess² − target| < epsilon.
# Approximate square root of 2 to within epsilon = 0.001
target = 2.0
epsilon = 0.001
increment = 0.0001
guess = 0.0
while abs(guess ** 2 - target) >= epsilon:
guess += increment
print(f'Approximate √2 = {guess:.4f}')
print(f'Error: {abs(guess**2 - target):.6f}')
increment must be much smaller than epsilon. If increment >= epsilon, the loop might step over the answer and never satisfy the condition — causing an infinite loop or a wrong answer.
0.1 + 0.2 == 0.3 # → False !
0.1 + 0.2 # → 0.30000000000000004
# Correct comparison: use a tolerance
abs((0.1 + 0.2) - 0.3) < 1e-10 # → True
Floats are stored in binary with ~15 significant digits of precision. Some decimal fractions (like 0.1) cannot be represented exactly in binary, so tiny rounding errors accumulate. Never use == to compare two floats — always check abs(a - b) < epsilon.
# Template: find x where f(x) ≈ target
target = ___ # what you're looking for
epsilon = ___ # how close is "close enough"
increment = ___ # step size (must be << epsilon)
guess = start_value # starting point
while abs(f(guess) - target) >= epsilon and guess <= upper_limit:
guess += increment
if abs(f(guess) - target) < epsilon:
print(f'Found: {guess:.4f}')
else:
print('No solution found in range')
| Function | Example → Result |
|---|---|
abs(x) | abs(-3.7) → 3.7 |
round(x, n) | round(3.14159, 2) → 3.14 |
max(a, b) | max(3, 7) → 7 |
min(a, b) | min(3, 7) → 3 |
x ** 0.5 | Square root (same as √x) |
What is the value and type of each expression?
7 / 2 # → ? (type: ?)
7 // 2 # → ? (type: ?)
7 % 2 # → ? (type: ?)
int(7 / 2) # → ? (type: ?)
str(7 // 2) # → ? (type: ?)
Given s = 'Engineering', what does each expression return?
s[0] # →
s[-3] # →
s[3:7] # →
s[:4] # →
len(s) # →
Trace this code. What does it print?
result = 0
for i in range(1, 6):
if i % 2 != 0:
result += i * i
print(result)
What does this code print? Trace each iteration.
n = 100
steps = 0
while n > 1:
if n % 2 == 0:
n = n // 2
else:
n = 3 * n + 1
steps += 1
if steps >= 5:
break
print(f'n={n}, steps={steps}')
n=19, steps=5
Write a while loop that approximates √7 to within epsilon = 0.0001 using steps of 0.00001, starting from guess = 0.0. Print the result with 4 decimal places.
target = 7.0
epsilon = 0.0001
increment = 0.00001
guess = 0.0
while abs(guess ** 2 - target) >= epsilon:
guess += increment
print(f'Approximate √7 = {guess:.4f}')
# Expected output: Approximate √7 = 2.6458
Each snippet has exactly one bug. Identify and fix it.
# Bug A
total = 0
for i in range(1, 11)
total = total + i
print(total)
# Bug B
x = 5.0
if x > 3 and x < 10
print('in range')
# Bug C
count = 10
while count > 0:
print(count)
count - 1 # intended to count down
for i in range(1, 11):if x > 3 and x < 10:count - 1 doesn't update the variable → change to count -= 1
| Mistake | Wrong | Correct |
|---|---|---|
| Missing colon | if x > 0 | if x > 0: |
| Not updating variable | count + 1 | count += 1 |
| Off-by-one in range | range(1, 5) for 1–5 | range(1, 6) |
| Comparing floats with == | x**2 == 2.0 | abs(x**2 - 2.0) < eps |
| int() rounds instead of truncates | Expecting int(3.9) = 4 | int(3.9) = 3 |
| String + number without conversion | 'Score: ' + 95 | 'Score: ' + str(95) or f-string |
| input() returns str, not int | n = input('...') then n + 1 | n = int(input('...')) |
| Increment too large in approximation | epsilon=0.001, increment=0.01 | increment must be ≪ epsilon |
| Wrong indentation level | Code inside loop that should be outside | Check every block carefully |
| Using = instead of == | if x = 5: | if x == 5: |