3.05 Boolean Expressions HW
3.05 Boolean Expressions
Source lesson: python/boolean
Learning Objective: Write and evaluate Boolean expressions that compare values and combine several backend requirements with and, or and not.
Submission notes
- Lesson: CSP 3.05 Boolean Expressions
- Notebook: https://jupiterian.opencodingsociety.com/python/boolean-hw
-
MCQ 3.05: 4/4 answers: A,C,A,B - Popcorn Hacks 1–3 completed during class and copied to notebook: yes
- Homework tested: supplied 3 records (accept / reject category / reject duplicate) plus 2 extra (empty name, empty date), all rejected for the right reason
Popcorn Hack 1: Check One SFI Part Record
Prediction: all four requirements are present and “Auto Racing” is in the accepted list, so every line prints True and the record is complete.
Code Runner Challenge
Popcorn Hack 1 - Check SFI Part Fields
View IPYNB Source
# CODE_RUNNER: Popcorn Hack 1 - Check SFI Part Fields
part = {
"product_name": "Replacement Flywheels and Clutch Assemblies",
"category": "Auto Racing",
"spec_number": "1.1",
"effective_date": "Nov. 9, 2001"
}
valid_categories = ["Auto Racing", "Drag Racing"]
has_product_name = part["product_name"] != ""
valid_category = part["category"] in valid_categories
has_spec_number = part["spec_number"] != ""
has_effective_date = part["effective_date"] != ""
print("Has product name:", has_product_name)
print("Valid racing category:", valid_category)
print("Has spec number:", has_spec_number)
print("Has effective date:", has_effective_date)
print("Record complete:", has_product_name and valid_category and has_spec_number and has_effective_date)
# Changed input: same record but a Street Car category
part["category"] = "Street Car"
valid_category = part["category"] in valid_categories
print("After changing category to Street Car -> valid category:", valid_category)
Actual output: all four checks and “Record complete” are True. After changing the category to “Street Car”, valid_category flips to False because it isn’t in the accepted list.
Popcorn Hack 2: Backend Create Rule
Create only when every required field is valid and the spec number is not already stored, so the rule is all_fields_valid and not duplicate_spec.
Prediction: spec "1.1" is already in existing_spec_numbers, so the first run should reject. Changing the spec to "3.1" should create.
Code Runner Challenge
Popcorn Hack 2 - Backend Create Rule
View IPYNB Source
# CODE_RUNNER: Popcorn Hack 2 - Backend Create Rule
part = {
"product_name": "Replacement Flywheels and Clutch Assemblies",
"category": "Auto Racing",
"spec_number": "1.1",
"effective_date": "Nov. 9, 2001"
}
valid_categories = ["Auto Racing", "Drag Racing"]
existing_spec_numbers = ["1.1", "2.1"]
for spec in ["1.1", "3.1"]: # rejected case, then valid case
part["spec_number"] = spec
all_fields_valid = (part["product_name"] != ""
and part["category"] in valid_categories
and part["spec_number"] != ""
and part["effective_date"] != "")
duplicate_spec = part["spec_number"] in existing_spec_numbers
should_create = all_fields_valid and not duplicate_spec
print("Spec", spec, "-> fields valid:", all_fields_valid, "| duplicate:", duplicate_spec, "| create:", should_create)
Actual output: spec 1.1 → fields valid True, duplicate True, create False. Spec 3.1 → fields valid True, duplicate False, create True. The only thing that changed is the duplicate check, and not flips it into the create decision.
Popcorn Hack 3: SFI Search Filter
A record matches when (query is in the product name OR query equals the spec number) AND the category is accepted. The parentheses matter: without them, and binds tighter than or, so a spec match would skip the category check.
Prediction: query "1.2" matches only the Multiple Disc Clutch record (spec 1.2, Drag Racing). Query "flywheel" matches both flywheel records (product names), and both are accepted categories.
Code Runner Challenge
Popcorn Hack 3 - SFI Search Filter
View IPYNB Source
# CODE_RUNNER: Popcorn Hack 3 - SFI Search Filter
records = [
{"product_name": "Replacement Flywheels and Clutch Assemblies", "category": "Auto Racing", "spec_number": "1.1"},
{"product_name": "Multiple Disc Clutch Assemblies", "category": "Drag Racing", "spec_number": "1.2"},
{"product_name": "Racing Flywheel Record", "category": "Auto Racing", "spec_number": "2.1"}
]
valid_categories = ["Auto Racing", "Drag Racing"]
for query in ["1.2", "flywheel", "9.9"]:
print("Query:", query)
found = False
for record in records:
name_match = query.lower() in record["product_name"].lower()
spec_match = query == record["spec_number"]
accepted = record["category"] in valid_categories
if (name_match or spec_match) and accepted:
print(" Match:", record["spec_number"], "-", record["product_name"])
found = True
if not found:
print(" No matching records")
Actual output: 1.2 → only spec 1.2. flywheel → specs 1.1 and 2.1. 9.9 → no matching records. The search is case-insensitive on the name (.lower() on both sides) and exact on the spec number.
MCQ
| **MCQ 3.05: 4/4 | answers: A,C,A,B** |
7 >= 7evaluates to: A True · B False · C 7 · D An error. A,>=includes equality.- Valid only with a name AND a spec number. Which operator? A or · B not · C and · D
!=. C, both must be true. duplicate_specis False. What isnot duplicate_spec? A True · B False · C None · D A string. A,notreverses it.- Which accepts either Auto Racing or Drag Racing? A
... and ...· Bcategory == 'Auto Racing' or category == 'Drag Racing'· Cnot category· Dcategory != 'Auto Racing'. B, only one comparison needs to be true. (A can never be true, since one category can’t equal both.)
Homework Hack: SFI Backend Validator
validate_record builds one named Boolean per rule, then combines them with and / not. It returns the decision plus the reasons, so every rejection says why. It’s self-contained, so it runs without the cells above.
| Rule | Boolean |
|---|---|
| non-empty product name | has_product_name = record["product_name"].strip() != "" |
| accepted category | valid_category = record["category"] in valid_categories |
| non-empty spec number | has_spec_number = record["spec_number"].strip() != "" |
| effective date present | has_effective_date = record["effective_date"].strip() != "" |
| spec not already stored | duplicate_spec = record["spec_number"] in existing_spec_numbers |
| accept | has_product_name and valid_category and has_spec_number and has_effective_date and not duplicate_spec |
Prediction: record 1 → ACCEPT. Record 2 → REJECT (Street Car is not an accepted category). Record 3 → REJECT (spec 1.1 already exists). Extra record 4 → REJECT (empty product name). Extra record 5 → REJECT (missing effective date).
Code Runner Challenge
Homework Hack - SFI Backend Validator
View IPYNB Source
# CODE_RUNNER: Homework Hack - SFI Backend Validator
existing_spec_numbers = ["1.1", "2.1"]
valid_categories = ["Auto Racing", "Drag Racing"]
test_records = [
{"product_name": "Multiple Disc Clutch Assemblies", "category": "Auto Racing", "spec_number": "1.2", "effective_date": "Feb. 9, 2006"},
{"product_name": "Replacement Flywheels", "category": "Street Car", "spec_number": "3.1", "effective_date": "Jan. 1, 2026"},
{"product_name": "Existing Flywheel Record", "category": "Drag Racing", "spec_number": "1.1", "effective_date": "Jan. 1, 2026"},
# extra edge cases
{"product_name": " ", "category": "Drag Racing", "spec_number": "4.1", "effective_date": "Mar. 3, 2026"},
{"product_name": "Harmonic Balancer", "category": "Auto Racing", "spec_number": "18.1", "effective_date": ""}
]
def validate_record(record):
has_product_name = record["product_name"].strip() != ""
valid_category = record["category"] in valid_categories
has_spec_number = record["spec_number"].strip() != ""
has_effective_date = record["effective_date"].strip() != ""
duplicate_spec = record["spec_number"] in existing_spec_numbers
is_valid = has_product_name and valid_category and has_spec_number and has_effective_date and not duplicate_spec
reasons = []
if not has_product_name:
reasons.append("missing product name")
if not valid_category:
reasons.append("category '" + record["category"] + "' not accepted")
if not has_spec_number:
reasons.append("missing spec number")
if not has_effective_date:
reasons.append("missing effective date")
if duplicate_spec:
reasons.append("spec " + record["spec_number"] + " already exists")
return is_valid, reasons
accepted = 0
for record in test_records:
is_valid, reasons = validate_record(record)
label = record["product_name"].strip() or "(no name)"
if is_valid:
accepted += 1
print("ACCEPT:", label, "(spec " + record["spec_number"] + ")")
else:
print("REJECT:", label, "->", ", ".join(reasons))
print("Accepted", accepted, "of", len(test_records), "records")
Actual output: ACCEPT for Multiple Disc Clutch Assemblies (spec 1.2). REJECT for Replacement Flywheels (category ‘Street Car’ not accepted), Existing Flywheel Record (spec 1.1 already exists), the blank-name record (missing product name), and Harmonic Balancer (missing effective date). 1 of 5 accepted. Matches the prediction.
| Test | Case | Expected | Actual |
|---|---|---|---|
| 1 | valid | ACCEPT | ACCEPT |
| 2 | invalid category | REJECT | REJECT, category |
| 3 | duplicate spec | REJECT | REJECT, duplicate |
| 4 | name is only spaces (edge) | REJECT | REJECT, name |
| 5 | empty date (edge) | REJECT | REJECT, date |
Why the logic is right: every requirement has to pass, so the rules are joined with and. A single False rejects the record. The duplicate rule is phrased as “does NOT already exist”, so it’s not duplicate_spec. Using .strip() before comparing to "" means a name made of spaces counts as empty (test 4). Without it, " " != "" is True and that record would have been accepted.
Pseudocode check (test 3): duplicateSpec ← (specNumber = "1.1") OR (specNumber = "2.1") is true, so NOT duplicateSpec is false. The whole AND chain is then false and the pseudocode displays REJECT RECORD, the same decision as the Python validator.