From 90217337b0421ee2fd875c7890cc9b0264cceb86 Mon Sep 17 00:00:00 2001 From: jm1021 Date: Sat, 9 Mar 2024 07:23:06 -0800 Subject: [PATCH] clean up and add code and hacks --- .../2024-03-12-CSP-MCQ-2020-missed.ipynb | 427 +++++------------- 1 file changed, 120 insertions(+), 307 deletions(-) diff --git a/_notebooks/2024-03-12-CSP-MCQ-2020-missed.ipynb b/_notebooks/2024-03-12-CSP-MCQ-2020-missed.ipynb index 9a879c8f..64608297 100644 --- a/_notebooks/2024-03-12-CSP-MCQ-2020-missed.ipynb +++ b/_notebooks/2024-03-12-CSP-MCQ-2020-missed.ipynb @@ -1,14 +1,14 @@ { "cells": [ { - "cell_type": "markdown", + "cell_type": "raw", "metadata": {}, "source": [ "---\n", "comments: true\n", "layout: post\n", "title: MCQ 2020 Frequently Missed Questions\n", - "description: Indiviual explanation on each of the 10 most missed questions.\n", + "description: Questions and sample Python code to represent the most frequently missed questions on the 2020 AP Computer Science A Multiple Choice Exam. \n", "type: collab\n", "courses: { csp: {week: 26} }\n", "---" @@ -46,21 +46,15 @@ }, { "cell_type": "code", - "execution_count": 13, + "execution_count": null, "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Max float: 1.7976931348623157e+308\n", - "Overflow float: inf\n" - ] - } - ], + "outputs": [], "source": [ - "\n", "# python overflow example\n", + "# as a popcorn hack (binary challenge), describe an overflow in 8 binary digits\n", + "# Add 1 to 11111111 (255)\n", + "# Subtract 1 from 00000000 (0)\n", + "\n", "import sys\n", "\n", "# Maximum float\n", @@ -86,8 +80,8 @@ "cell_type": "markdown", "metadata": {}, "source": [ - "The diagram below shows a circuit composed of three logic gates. Each gate takes two inputs and produces a single output.
\n", - "
\n", + "The diagram in question shows a circuit composed of three logic gates. Each gate takes two inputs and produces a single output.
\n", + "\n", "For which of the following input values will the circuit have an output of true ?
\n", "\n", "A) A = true, B = true, C = true, D = false
\n", @@ -101,35 +95,14 @@ }, { "cell_type": "code", - "execution_count": 39, + "execution_count": null, "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "A B C D Output\n", - "False False False False --> False\n", - "False False False True --> False\n", - "False False True False --> False\n", - "False False True True --> False\n", - "False True False False --> False\n", - "False True False True --> False\n", - "False True True False --> False\n", - "False True True True --> True\n", - "True False False False --> False\n", - "True False False True --> False\n", - "True False True False --> False\n", - "True False True True --> True\n", - "True True False False --> False\n", - "True True False True --> False\n", - "True True True False --> False\n", - "True True True True --> True\n" - ] - } - ], + "outputs": [], "source": [ "# represent gates and circuits\n", + "# as a popcorn hack (coding challenge), create multiple new circuits and gates\n", + "# NOT, NAND, NOR, XOR, XNOR\n", + "# Create a hypothetical circuit, such as burglar alarm, decision tree for autonomous car, etc.\n", "\n", "# OR gate\n", "def OR_gate(A, B):\n", @@ -139,12 +112,18 @@ "def AND_gate(A, B):\n", " return A and B\n", "\n", - "# Circuit representing correct behavior\n", + "# Theoritical circuit representing a Car starting\n", + "# A and B could be security checks, such as key being inserted or a fob being present\n", + "# C and D could be operational checks, such as a start button being pressed and safety belt being fastened\n", + "# The enclosing AND gate ensures car only operates when both security and operational checks are met\n", "def circuit(A, B, C, D):\n", " return AND_gate(OR_gate(A, B), AND_gate(C, D))\n", "\n", "# Print truth table for circuit\n", - "print('A', 'B', 'C', 'D', 'Output')\n", + "print('A', 'B', 'C', 'D', \"-->\", 'Output')\n", + "# nesting of loops for both the True, False combination of A, B, C, D \n", + "# this algorithm is 2 ^ 4 = 16, thus producing all 16 combinations \n", + "# each combination terminates with the output of the circuit\n", "for A in [False, True]:\n", " for B in [False, True]:\n", " for C in [False, True]:\n", @@ -184,30 +163,13 @@ }, { "cell_type": "code", - "execution_count": 32, + "execution_count": null, "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "00111111 00111111 01110000\n", - "0.24705882352941178 0.24705882352941178 0.4392156862745098\n" - ] - }, - { - "data": { - "image/png": "iVBORw0KGgoAAAANSUhEUgAAAK8AAACuCAYAAABAzl3QAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjguMywgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/H5lhTAAAACXBIWXMAAA9hAAAPYQGoP6dpAAACA0lEQVR4nO3UsQmEABBFwfOwMFu6SmzJztbsYhFEHszEG/zgscvMzAeCvm8PgLvES5Z4yRIvWeIlS7xkiZcs8ZIlXrLWq4fb9ntyB/wdx37pzuclS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIlS7xkiZcs8ZIlXrLES5Z4yRIvWeIla5mZeXsE3OHzkiVessRLlnjJEi9Z4iVLvGSJlyzxknUCIWEMVYqM7EcAAAAASUVORK5CYII=", - "text/plain": [ - "
" - ] - }, - "metadata": {}, - "output_type": "display_data" - } - ], + "outputs": [], "source": [ "# Convert binary RGB triplet to decimal\n", + "# as a hack (binary challenge), make the rgb standard colors\n", + "# as a 2nd hack, make your favorite color pattern \n", "\n", "import matplotlib.pyplot as plt\n", "import matplotlib.patches as patches\n", @@ -216,66 +178,47 @@ "def binary_to_decimal(binary):\n", " return int(binary, 2)\n", "\n", - "# Binary RGB triplet, example by College Board was 11111111, 11111111, 11110000; almost white \n", - "red_binary = '00111111'\n", - "green_binary = '00111111'\n", - "blue_binary = '01110000'\n", - "\n", - "# Convert to binary strings to decimal\n", - "red = binary_to_decimal(red_binary)\n", - "green = binary_to_decimal(green_binary)\n", - "blue = binary_to_decimal(blue_binary)\n", - "\n", - "# Normalize number to [0, 1] range, as it is expected by matplotlib \n", - "red, green, blue = red/255, green/255, blue/255\n", - "\n", - "# Create a figure and a subplot\n", - "fig, ax = plt.subplots(1, 1, figsize=(2, 2))\n", - "\n", - "# Create a rectangle patch on the subplot with the color\n", - "rect = patches.Rectangle((0, 0), 1, 1, facecolor=(red, green, blue))\n", - "\n", - "# Add the patch to the Axes\n", - "ax.add_patch(rect)\n", - "\n", - "# Remove axis\n", - "ax.axis('off')\n", - "\n", - "# Print the binary and decimal values\n", - "print(red_binary, green_binary, blue_binary) \n", - "print(red, green, blue)\n", - "# Show the triplet color\n", - "plt.show()" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "## 15. Compare output of program a and b (1D, program loop) - Arnav Nadar\n", - "\n", - "Which of the following best compares the values displayed by programs A and B?\n", - "\n" - ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "## 23. Flowchart to set available (1D, algorithmic expression) - Tanujsai Nimmagadda\n", - "\n", - "A flowchart is a way to visually represent an algorithm. The flowchart below is used by an application to set the Boolean variable available to true under certain conditions. The flowchart uses the Boolean variable weekday and the integer variable miles.\n", - "\n", - "Which of the following statements is equivalent to the algorithm in the flowchart?\n", - "\n", - "\n", - "\n", - " - Within this diagram, the circle functions are the start and end of the program. The rectangular boxes are the output and the diamonds are the deciding booleans. \n", - " - Using these functions, the program comes to its output of either available being true or false. The program must go through the requirements to get the value true, which the problem asks of us, the variable weekday equals true and the variable miles should be less than 20. These both must be true and cannot result from one or the other happening. \n", - "\n", - "The answer was meant to be D.\n", - "\n", - "\n" + "def plot_colors(rgb_triplets):\n", + " # Create a figure with one subplot per RGB triplet\n", + " fig, axs = plt.subplots(1, len(rgb_triplets), figsize=(2 * len(rgb_triplets), 2))\n", + " \n", + " # Ensure axs is always a list\n", + " axs = axs if len(rgb_triplets) > 1 else [axs]\n", + "\n", + " for ax, (red_binary, green_binary, blue_binary) in zip(axs, rgb_triplets):\n", + " # Convert to binary strings to decimal\n", + " red_decimal = binary_to_decimal(red_binary)\n", + " green_decimal = binary_to_decimal(green_binary)\n", + " blue_decimal = binary_to_decimal(blue_binary)\n", + "\n", + " # Normalize number to [0, 1] range, as it is expected by matplotlib \n", + " red, green, blue = red_decimal/255, green_decimal/255, blue_decimal/255\n", + "\n", + " # Define a rectangle patch with the binary RGB triplet color and a black border\n", + " rect = patches.Rectangle((0, 0), 1, 1, facecolor=(red, green, blue), edgecolor='black', linewidth=2)\n", + " \n", + " # Add the rectangle to the plot which shows the color \n", + " ax.add_patch(rect)\n", + "\n", + " # Remove axis information, we just want to see the color\n", + " ax.axis('off')\n", + "\n", + " # Print the binary and decimal values\n", + " print(\"binary:\", red_binary, green_binary, blue_binary) \n", + " print(\"decimal\", red_decimal, green_decimal, blue_decimal)\n", + " print(\"proportion\", red, green, blue)\n", + "\n", + " # Show the colors\n", + " plt.show()\n", + "\n", + "# Test the function with a list of RGB triplets\n", + "rgb_triplet = [('11111111', '11111111', '11110000')] # College Board example\n", + "plot_colors(rgb_triplet)\n", + "\n", + "rgb_primary = [('11111111', '00000000', '00000000'), \n", + " ('11111111', '11111111', '00000000'),\n", + " ('00000000', '00000000', '11111111')]\n", + "plot_colors(rgb_primary)" ] }, { @@ -286,12 +229,17 @@ "\n", "Consider the following algorithms. Each algorithm operates on a list containing n elements, where n is a very large integer.\n", "\n", - "An algorithm that accesses each element in the list twice\n", - "An algorithm that accesses each element in the list n times\n", - "An algorithm that accesses only the first 10 elements in the list, regardless of the size of the list\n", - "Which of the algorithms run in reasonable time?\n", + "- An algorithm that accesses each element in the list twice\n", + "- An algorithm that accesses each element in the list n times\n", + "- An algorithm that accesses only the first 10 elements in the list, regardless of the size of the list\n", "\n", - "Answer D is correct because in order for an algorithm to run in reasonable time, it must take a number of steps less than or equal to a polynomial function. Algorithm I accesses elements times (twice for each of n elements), which is considered in time. Algorithm II accesses elements (n times for each of n elements), which is in reasonable time. Algorithm III accesses 10 elements, which is in reasonable time.\n", + "\n", + "Which of the algorithms run in reasonable time?\n", + "Answer D is correct because in order for an algorithm to run in reasonable time, it must take a number of steps less than or equal to a polynomial function.\n", + " \n", + "- Algorithm I accesses elements times (twice for each of n elements), which is considered in time. \n", + "- Algorithm II accesses elements (n times for each of n elements), which is in reasonable time. \n", + "- Algorithm III accesses 10 elements, which is in reasonable time.\n", "\n", "Simple Explainations:\n", "\n", @@ -302,37 +250,34 @@ }, { "cell_type": "code", - "execution_count": 34, + "execution_count": null, "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Algorithm 1 took 0.13 milliseconds\n", - "Algorithm 2 took 378.27 milliseconds\n", - "Algorithm 3 took 0.02 milliseconds\n" - ] - } - ], + "outputs": [], "source": [ + "# Big O notation example algorithms\n", + "# as a popcorn hack (coding challenge), scale list of size by factor of 10 and measure the times\n", + "# what do you think about college board's notion of reasonable time for an algorithm?\n", + "# as a 2nd hack, create a slow algorithm and measure its time, which are considered slow algorithms... \n", + "# O(n^3) which is three nested loops \n", + "# O(2^n) which is a recursive algorithm with two recursive calls\n", + "\n", "import time\n", "\n", - "# Algorithm that accesses each element in the list twice\n", - "def algorithm1(lst):\n", + "# O(n) Algorithm that accesses each element in the list twice, 2 * n times \n", + "def algorithm_2n(lst):\n", " for i in lst:\n", " pass\n", " for i in lst:\n", " pass\n", "\n", - "# Algorithm that accesses each element in the list n times\n", - "def algorithm2(lst):\n", + "# O(n^2) Algorithm that accesses each element in the list n times, n * n times\n", + "def algorithm_nSquared(lst):\n", " for i in lst:\n", " for j in lst:\n", " pass\n", "\n", - "# Algorithm that accesses only the first 10 elements in the list\n", - "def algorithm3(lst):\n", + "# O(1) Algorithm that accesses only the first 10 elements in the list, 10 * 1 is constant \n", + "def algorithm_10times(lst):\n", " for i in lst[:10]:\n", " pass\n", "\n", @@ -342,21 +287,21 @@ "\n", "# Measure the time taken by algorithm1\n", "start = time.time()\n", - "algorithm1(lst)\n", + "algorithm_2n(lst)\n", "end = time.time()\n", - "print(f\"Algorithm 1 took {(end - start)*1000:.2f} milliseconds\")\n", + "print(f\"Algorithm 2 * N took {(end - start)*1000:.2f} milliseconds\")\n", "\n", "# Measure the time taken by algorithm2\n", "start = time.time()\n", - "algorithm2(lst)\n", + "algorithm_nSquared(lst)\n", "end = time.time()\n", - "print(f\"Algorithm 2 took {(end - start)*1000:.2f} milliseconds\")\n", + "print(f\"Algorithm N^2 took {(end - start)*1000:.2f} milliseconds\")\n", "\n", "# Measure the time taken by algorithm3\n", "start = time.time()\n", - "algorithm3(lst)\n", + "algorithm_10times(lst)\n", "end = time.time()\n", - "print(f\"Algorithm 3 took {(end - start)*1000:.2f} milliseconds\")" + "print(f\"Algorithm 10 times took {(end - start)*1000:.2f} milliseconds\")" ] }, { @@ -386,82 +331,18 @@ "metadata": {}, "outputs": [], "source": [ - "Version I\n", - "\n", - "topScore \n", - " 0\n", - "\n", - "idList \n", - " [1298702, 1356846, 8848491, 8675309]\n", - "\n", - "FOR EACH id IN idList\n", - "\n", - "{\n", - "\n", - "score \n", - " GetPrediction (id)\n", - "\n", - "IF (score > topScore)\n", - "\n", - "{\n", - "\n", - "topScore \n", - " score\n", - "\n", - "}\n", - "\n", - "}\n", - "\n", - "DISPLAY (topScore)\n", - "\n", - "Version II\n", - "\n", - "idList \n", - " [1298702, 1356846, 8848491, 8675309]\n", - "\n", - "topID \n", - " idList[1]\n", - "\n", - "FOR EACH id IN idList\n", - "\n", - "{\n", - "\n", - "IF (GetPrediction (id) > GetPrediction (topID))\n", - "\n", - "{\n", - "\n", - "topID \n", - " id\n", - "\n", - "}\n", - "\n", - "}\n", - "\n", - "DISPLAY (GetPrediction (topID)) " - ] - }, - { - "cell_type": "code", - "execution_count": 40, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "Version I took 240.00000095367432 seconds\n", - "Version II took 540.0000011920929 seconds\n" - ] - } - ], - "source": [ - "# Simulate the time taken by GetPrediction\n", + "# Simulate the time taken by GetPrediction, calling an expensive operation twice is slow\n", + "# as a popcorn hack (coding challenge)\n", + "# measure the time to calulate fibonacci sequence at small and large numbers\n", + "# `this task will require a code layout and a time measurement\n", + "# there are fast ways and slow ways to calculate fibonacci sequence`\n", "\n", "'''\n", "The GetPrediction function is a simulation stand-in for a potentially expensive operation.\n", "In a real-world scenario, this could be a call to a;\n", " - machine learning model\n", " - a database query\n", + " - fibonacci sequence at a large number\n", " - or any other algorithm that takes a significant amount of time.\n", "'''\n", "def GetPrediction(idNum):\n", @@ -474,10 +355,10 @@ " topScore = 0\n", " for idNum in idList:\n", " predictedScore = GetPrediction(idNum) # calls GetPrediction once\n", - " if predictedScore > topScore:\n", - " topScore = predictedScore\n", + " if predictedScore > topScore: \n", + " topScore = predictedScore # stores the topScore to avoid calling GetPrediction again\n", " end = time.time() # End timer\n", - " print(f\"Version I took {end - start + len(idList) * 60} simulated seconds\") # Add simulated delay\n", + " print(f\"Version I took {end - start + len(idList) * 60:.2f} simulated seconds\") # Add simulated delay\n", "\n", "# Version II: makes two calls to GetPrediction for each element in idList\n", "def version_II(idList):\n", @@ -485,12 +366,13 @@ " topID = idList[0]\n", " for idNum in idList:\n", " if GetPrediction(idNum) > GetPrediction(topID): # calls GetPrediction twice\n", - " topID = idNum\n", + " topID = idNum # stores the topID, but still calls GetPrediction with topID again\n", " end = time.time() # End timer\n", - " print(f\"Version II took {end - start + len(idList) * 2 * 60 + 60} simulated seconds\") # Add simulated delay\n", + " print(f\"Version II took {end - start + len(idList) * 2 * 60 + 60:.2f} simulated seconds\") # Add simulated delay\n", "\n", "# Test the functions\n", - "idList = [1, 2, 3, 4]\n", + "idList = [1, 2, 3, 4] # Small list\n", + "# idList = [i for i in range(1, 1000)] # Large list using list comprehension\n", "version_I(idList)\n", "version_II(idList)" ] @@ -548,23 +430,15 @@ }, { "cell_type": "code", - "execution_count": 36, + "execution_count": null, "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "10\n", - "0\n", - "-10\n", - "0\n" - ] - } - ], + "outputs": [], "source": [ + "# flawed multiply function\n", + "# as a popcorn hack (coding challenge), fix the multiply function to work with negative numbers\n", + "\n", "'''\n", - "As you can see, the function fails when y is negativei,\n", + "As you can see, the function fails when y is negative,\n", "because the while loop condition count < y is never true in these cases.\n", "'''\n", "\n", @@ -583,43 +457,6 @@ "print(multiply(-2, -5)) # Expected output: 10, Actual output: 0" ] }, - { - "cell_type": "code", - "execution_count": 37, - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "10\n", - "-10\n", - "-10\n", - "10\n" - ] - } - ], - "source": [ - "'''\n", - "As you can see, the function fails when y is negativei,\n", - "because the while loop condition count < y is never true in these cases.\n", - "'''\n", - "\n", - "def multiply(x, y):\n", - " count = 0\n", - " result = 0\n", - " while abs(count) < abs(y):\n", - " result += x if y > 0 else -x\n", - " count += 1\n", - " return result\n", - "\n", - "# Test cases\n", - "print(multiply(2, 5)) # Expected output: 10\n", - "print(multiply(2, -5)) # Expected output: -10\n", - "print(multiply(-2, 5)) # Expected output: -10\n", - "print(multiply(-2, -5)) # Expected output: 10" - ] - }, { "cell_type": "markdown", "metadata": {}, @@ -652,19 +489,6 @@ "The process outlined in Answer B does indeed result in the string “jackalope”, with the first step isolating “lope” from “antelope”, the second step creating the string “alope” by prepending “a” to “lope”, and the final step creating the correct string by prepending “jack” to “alope”." ] }, - { - "cell_type": "code", - "execution_count": null, - "metadata": {}, - "outputs": [], - "source": [ - "# Correct Answer C\n", - "animal = \"jackrabbit\"[0:4] # Substring(\"jackrabbit\", 1, 4)\n", - "animal += \"a\" # Concat(animal, \"a\")\n", - "animal += \"antelope\"[4:8] # Concat(animal, Substring(\"antelope\", 5, 4))\n", - "print(animal) # Outputs: jackalope" - ] - }, { "cell_type": "code", "execution_count": null, @@ -672,24 +496,13 @@ "outputs": [], "source": [ "# Incorrect Answer D\n", + "# as a popcorn hack (binary challenge), create string and concatenation options for A, B, C\n", + " \n", "animal = \"jackrabbit\"[0:4] # Substring(\"jackrabbit\", 1, 4)\n", "animal += \"a\" # Concat(animal, \"a\")\n", "animal = \"antelope\"[4:8] + animal # Concat(Substring(\"antelope\", 5, 4), animal)\n", "print(animal) # Outputs: lopejacka" ] - }, - { - "cell_type": "markdown", - "metadata": {}, - "source": [ - "## 67. Error in numOccurrences procedure (4C algorithms and programs) - Monika Roy\n", - "\n", - "The procedure NumOccurrences is intended to count and return the number of times targetWord appears in the list wordList. The procedure does not work as intended.\n", - "\n", - "For which of the following code segments will the call to NumOccurrences NOT return the intended value?\n", - "\n", - "Select two answers. " - ] } ], "metadata": {