# Numpy 3 --- title: Agenda description: duration: 300 card_type: cue_card --- ### Content - Sorting - Matrix Multiplication - `np.dot` - `@` operator - `np.matmul` - Vectorization - Broadcasting --- title: Sorting description: duration: 1200 card_type: cue_card --- ## Sorting - `np.sort` returns a sorted copy of an array. Code ```python= import numpy as np a = np.array([4, 7, 0, 3, 8, 2, 5, 1, 6, 9]) a ``` > Output array([4, 7, 0, 3, 8, 2, 5, 1, 6, 9]) Code ```python= b = np.sort(a) b ``` > Output array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9]) Code ```python= a # no change is reflected in the original array ``` > Output array([4, 7, 0, 3, 8, 2, 5, 1, 6, 9]) #### We can directly call `sort` method on array but it can change the original array as it is an inplace operation. Code ```python= a.sort() # sorting is performed inplace a ``` > Output array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9]) ### Sorting in 2D array Code ```python= a = np.array([[1,5,3], [2,5,7], [400, 200, 300]]) a ``` > Output array([[ 1, 5, 3], [ 2, 5, 7], [400, 200, 300]]) Code ```python= np.sort(a, axis=0) # sorting every column ``` > Output array([[ 1, 5, 3], [ 2, 5, 7], [400, 200, 300]]) Code ```python= np.sort(a, axis=1) # sorting every row ``` > Output array([[ 1, 3, 5], [ 2, 5, 7], [200, 300, 400]]) **Note**: By default, the `np.sort()` functions sorts along the last axis. --- title: Quiz-1 description: Quiz-1 duration: 60 card_type: quiz_card --- # Question What will be value of `b`? ```python= a = np.array([[23,4,43], [12,89,3], [69,420,0]]) b = np.sort(a) ``` ``` A. [[ 0, 3, 4], [ 12, 23, 43], [ 69, 89, 420]] B. [[ 4, 23, 43], [ 3, 12, 89], [ 0, 69, 420]] C. [[ 0, 12, 43], [ 3, 23, 89], [ 4, 69, 420]] ``` # Choices - [ ] A - [x] B - [ ] C - [ ] None of the above --- title: Element-wise Multiplication description: duration: 1500 card_type: cue_card --- ### Quiz-1 Explanation It will sort the array by last axis when no axis argument is provided. In this case, last axis will `axis=1`. Code ```python= a = np.array([[23,4,43], [12, 89, 3], [69, 420, 0]]) np.sort(a) # default axis = -1 (last axis) ``` > Output array([[ 4, 23, 43], [ 3, 12, 89], [ 0, 69, 420]]) ## Element-wise Multiplication Element-wise multiplication in NumPy involves multiplying corresponding elements of two arrays with the same shape to produce a new array where each element is the product of the corresponding elements from the input arrays. Code ```python= a = np.arange(1, 6) a ``` > Output array([1, 2, 3, 4, 5]) Code ```python= a * 5 ``` > Output array([ 5, 10, 15, 20, 25]) Code ```python= b = np.arange(6, 11) b ``` > Output array([ 6, 7, 8, 9, 10]) Code ```python= a * b ``` > Output array([ 6, 14, 24, 36, 50]) Both arrays should have the same shape. Code ```python= c = np.array([1, 2, 3]) a * c ``` > Output --------------------------------------------------------------------------- ValueError Traceback (most recent call last) <ipython-input-9-6e2761d948ae> in <cell line: 1>() ----> 1 a * c 2 # a and c do not have the same shape ValueError: operands could not be broadcast together with shapes (5,) (3,) Code ```python= d = np.arange(12).reshape(3, 4) e = np.arange(13, 25).reshape(3, 4) ``` ```python= print(d) print(e) ``` > Output [[ 0 1 2 3] [ 4 5 6 7] [ 8 9 10 11]] [[13 14 15 16] [17 18 19 20] [21 22 23 24]] Code ```python= d * e ``` > Output array([[ 0, 14, 30, 48], [ 68, 90, 114, 140], [168, 198, 230, 264]]) Code ```python= d * 5 ``` > Output array([[ 0, 5, 10, 15], [20, 25, 30, 35], [40, 45, 50, 55]]) **Takeaway:** - Array \* Number $\rightarrow$ WORKS - Array \* Array (same shape) $\rightarrow$ WORKS - Array \* Array (different shape) $\rightarrow$ DOES NOT WORK --- title: Matrix Multiplication description: duration: 1500 card_type: cue_card --- ## Matrix Multiplication **Rule:** Number of columns of the first matrix should be equal to number of rows of the second matrix. - (A,B) \* (B,C) -> (A,C) - (3,4) \* (4,3) -> (3,3) Visual Demo: <https://www.geogebra.org/m/ETHXK756> Code ```python= a = np.arange(1,13).reshape((3,4)) c = np.arange(2,14).reshape((4,3)) a.shape, c.shape ``` > Output ((3, 4), (4, 3)) ##### `a` is of shape (3,4) and `c` is of shape (4,3). The output will be of shape (3,3). Code ```python= # Using np.dot np.dot(a,c) ``` > Output array([[ 80, 90, 100], [184, 210, 236], [288, 330, 372]]) Code ```python= # Using np.matmul np.matmul(a,c) ``` > Output array([[ 80, 90, 100], [184, 210, 236], [288, 330, 372]]) Code ```python= # Using @ operator a@c ``` > Output array([[ 80, 90, 100], [184, 210, 236], [288, 330, 372]]) Code ```python= a@5 ``` > Output --------------------------------------------------------------------------- ValueError Traceback (most recent call last) <ipython-input-19-16572c98568d> in <cell line: 1>() ----> 1 a@5 ValueError: matmul: Input operand 1 does not have enough dimensions (has 0, gufunc core with signature (n?,k),(k,m?)->(n?,m?) requires 1) Code ```python= np.matmul(a, 5) ``` > Output --------------------------------------------------------------------------- ValueError Traceback (most recent call last) <ipython-input-20-875bf147741b> in <cell line: 1>() ----> 1 np.matmul(a, 5) ValueError: matmul: Input operand 1 does not have enough dimensions (has 0, gufunc core with signature (n?,k),(k,m?)->(n?,m?) requires 1) Code ```python= np.dot(a, 5) ``` > Output array([[ 5, 10, 15, 20], [25, 30, 35, 40], [45, 50, 55, 60]]) **Important:** - `dot()` function supports the vector multiplication with a scalar value, which is not possible with `matmul()`. - `Vector * Vector` will work for `matmul()` but `Vector * Scalar` won't. --- title: Quiz-2 description: Quiz-2 duration: 60 card_type: quiz_card --- # Question What will be the shape of the output? ```python= A = np.arange(10).reshape(5,2) B = np.arange(2).reshape(2,1) print(np.dot(A,B)) ``` # Choices - [ ] (5,2) - [ ] (5,) - [x] (5,1) --- title: Break & Doubt Resolution description: duration: 600 card_type: cue_card --- ### Break & Doubt Resolution `Instructor Note:` * Take this time (up to 5-10 mins) to give a short break to the learners. * Meanwhile, you can ask the them to share their doubts (if any) regarding the topics covered so far. --- title: Vectorization description: duration: 1500 card_type: cue_card --- ## Vectorization Vectorization in NumPy refers to performing operations on entire arrays or array elements simultaneously, which is significantly faster and more efficient than using explicit loops. Code ```python= a = np.arange(10) a ``` > Output array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9]) **Note:** - 1D np array $\rightarrow$ vector - 2D np array $\rightarrow$ matrix - 3D onwards $\rightarrow$ tensors Code ```python= def random_operation(x): if x % 2 == 0: x += 2 else: x -= 2 return x random_operation(a) ``` > Output --------------------------------------------------------------------------- ValueError Traceback (most recent call last) <ipython-input-18-83503709589d> in <cell line: 1>() ----> 1 random_operation(a) <ipython-input-17-1b21f73a20a9> in random_operation(x) 1 def random_operation(x): ----> 2 if x % 2 == 0: 3 x += 2 4 else: 5 x -= 2 ValueError: The truth value of an array with more than one element is ambiguous. Use a.any() or a.all() Code ```python= cool_operation = np.vectorize(random_operation) type(cool_operation) ``` > Output numpy.vectorize #### `np.vectorize()` - It is a generalised function for vectorization. - It takes the function and returns an object (which acts like function but can take an array as input and perform the operations). Code ```python= cool_operation(a) ``` > Output array([ 2, -1, 4, 1, 6, 3, 8, 5, 10, 7]) --- title: Broadcasting description: duration: 1800 card_type: cue_card --- ## Broadcasting Broadcasting in NumPy is the automatic and implicit extension of array dimensions to enable element-wise operations between arrays with different shapes. ![bro.jpg](https://d2beiqkhq929f0.cloudfront.net/public_assets/assets/000/047/364/original/download.jpeg?1694345633) #### **Case 1:** If dimension in both matrix is equal, element-wise addition will be done. Code ```python= a = np.tile(np.arange(0,40,10), (3,1)) a ``` > Output array([[ 0, 10, 20, 30], [ 0, 10, 20, 30], [ 0, 10, 20, 30]]) **Note:** - `numpy.tile(array, reps)` constructs an array by repeating `a` the number of times given by reps along each dimension. - `np.tile(array, (repetition_rows, repetition_cols))` Code ```python= a=a.T a ``` > Output array([[ 0, 0, 0], [10, 10, 10], [20, 20, 20], [30, 30, 30]]) Code ```python= b = np.tile(np.arange(0,3), (4,1)) b ``` > Output array([[0, 1, 2], [0, 1, 2], [0, 1, 2], [0, 1, 2]]) Code ```python= print(a.shape, b.shape) ``` > Output (4, 3) (4, 3) Since `a` and `b` have the same shape, they can be added without any issues. Code ```python= a+b ``` > Output array([[ 0, 1, 2], [10, 11, 12], [20, 21, 22], [30, 31, 32]]) #### **Case 2:** Right array should be of 1-D and number of columns should be same of both the arrays and it will automatically do n-tile. Code ```python= a ``` > Output array([[ 0, 0, 0], [10, 10, 10], [20, 20, 20], [30, 30, 30]]) Code ```python= c = np.array([0,1,2]) c ``` > Output array([0, 1, 2]) Code ```python= print(a.shape, c.shape) ``` > Output (4, 3) (3,) Code ```python= a + c ``` > Output array([[ 0, 1, 2], [10, 11, 12], [20, 21, 22], [30, 31, 32]]) - `c` was broadcasted along rows (vertically) - so that `a` and `c` can be made compatible #### **Case 3:** If the left array is column matrix (must have only 1 column) and right array is row matrix, then it will do the n-tile such that element wise addition is possible. Code ```python= d = np.array([0,10,20,30]).reshape(4,1) d ``` > Output array([[ 0], [10], [20], [30]]) Code ```python= c = np.array([0,1,2]) c ``` > Output array([0, 1, 2]) Code ```python= print(d.shape, c.shape) ``` > Output (4, 1) (3,) Code ```python= d + c ``` > Output array([[ 0, 1, 2], [10, 11, 12], [20, 21, 22], [30, 31, 32]]) - `d` was stacked (broadcasted) along columns (horizontally) - `c` was stacked (broadcasted) along rows (vertically) **Will broadcasting work in this case?** Code ```python= a = np.arange(8).reshape(2,4) a ``` > Output array([[0, 1, 2, 3], [4, 5, 6, 7]]) Code ```python= b = np.arange(16).reshape(4,4) b ``` > Output array([[ 0, 1, 2, 3], [ 4, 5, 6, 7], [ 8, 9, 10, 11], [12, 13, 14, 15]]) Code ```python= a+b ``` > Output --------------------------------------------------------------------------- ValueError Traceback (most recent call last) <ipython-input-45-ca730b97bf8a> in <cell line: 1>() ----> 1 a+b ValueError: operands could not be broadcast together with shapes (2,4) (4,4) #### Broadcasting in 2D Arrays - A + A (same shape) $\rightarrow$ WORKS - A + A (1D) $\rightarrow$ WORKS - A + number $\rightarrow$ WORKS - A + A (different shape but still 2D) $\rightarrow$ DOES NOT WORK **Is broadcasting possible in this case?** Code ```python= A = np.arange(1,10).reshape(3,3) A ``` > Output array([[1, 2, 3], [4, 5, 6], [7, 8, 9]]) Code ```python= B = np.array([-1, 0, 1]) B ``` > Output array([-1, 0, 1]) Code ```python= A*B ``` > Output array([[-1, 0, 3], [-4, 0, 6], [-7, 0, 9]]) Yes! Broadcasting is possible for all the operations. --- title: Quiz-3 description: Quiz-3 duration: 60 card_type: quiz_card --- # Question What will be the output of `A + B` ? ```python= A = np.arange(12).reshape(3, 4) B = np.array([1, 2, 3]) print(A+B) ``` ``` A. [[0, 1, 2, 3], [4, 5, 6, 7], [8, 9, 10, 11]] B. [[1, 2, 3, 4], [6, 7, 8, 9], [11,12,13,14]] C. Error ``` # Choices - [ ] A - [ ] B - [x] C --- title: Quiz-3 Explanation description: duration: 300 card_type: cue_card --- ### Quiz-3 Explanation Code ```python= A = np.arange(12).reshape(3, 4) A ``` > Output array([[ 0, 1, 2, 3], [ 4, 5, 6, 7], [ 8, 9, 10, 11]]) Code ```python= B = np.array([1, 2, 3]) B ``` > Output array([1, 2, 3]) Code ```python= A + B ``` > Output --------------------------------------------------------------------------- ValueError Traceback (most recent call last) <ipython-input-51-151064de832d> in <cell line: 1>() ----> 1 A + B ValueError: operands could not be broadcast together with shapes (3,4) (3,) **Why did it throw an error?** Are the number of dimensions same for both array? No. - Shape of A $\Rightarrow$ (3,4) - Shape of B $\Rightarrow$ (3,) So, `Rule 1` will be invoked to pad 1 to the shape of B. So, the shape of B becomes **(1,3)**. \ Now, we check whether broadcasting conditions are met or not? Starting from the right most side, - Right most dimension is not equal (4 and 3). Hence, broadcasting is not possible as per `Rule 3`. --- title: Quiz-4 description: Quiz-4 duration: 60 card_type: quiz_card --- # Question Given two arrays, 1. Array `A` of shape (8, 1, 6, 1) 2. Array `B` of shape (7, 1, 5) Is broadcasting possible in this case? If yes, what will be the shape of output? # Choices - [ ] Broadcasting not possible as dimensions don't match - [ ] Broadcasting not possible as dimension value 6 and 5 doesn't match - [ ] Broadcasting possible. Shape will be (8, 1, 6, 5) - [x] Broadcasting possible; Shape will be (8, 7, 6, 5) --- title: Quiz-4 Explanation description: duration: 300 card_type: cue_card --- ### Quiz-4 Explanation As number of dimensions are not equal, `Rule 1` is invoked. The shape of B becomes (1, 7, 1, 5) Next, it checks whether broadcasting is possible. A $\Rightarrow$ (8 , 1, 6, 1) \ B $\Rightarrow$ (1, 7, 1, 5) - Right most dimension, one of the dimension is 1 (1 vs 5) - Next, comparing 6 and 1, We have one dimension as 1 - Similarly, we have one of the dimension as 1 in both leading dimensions. Hence, broadcasting is possible. Now, as per `Rule 2`, dimension with value 1 is streched to match dimension of other array. - Right most dimension of array is streched to match 5 - Leading dimension of array B (1) is streched to match array A dim (6) So, the output shape becomes : `(8, 7, 6, 5)`. --- title: Launch a feedback poll description: To gather valuable feedback regarding pace adjustment duration: 30 card_type: poll_card --- # Description Which of the following best depicts your current level of confidence about the pace and difficulty of the material covered in the last 3 lectures? # Choices - Super confident: Feeling super confident and comfortable with pace, ready to conquer the next lesson. - Somewhat confident: Grasping most concepts and comfortable with content & pace, but a few concepts need brushing up. - Not so confident: While I understand some concepts, I'm finding the pace a bit too fast at times. - Feeling a bit lost: I'm finding it difficult to keep up with the pace or grasp certain topics. - Completely lost: I'm struggling significantly with the pace and difficulty of the material. --- title: Unlock Assignment & ask learner to solve in live class description: duration: 1800 card_type: cue_card --- * <span style=“color:skyblue”>Unlock the assignment for learners</span> by clicking the **“question mark”** button on the top bar. <img src="https://d2beiqkhq929f0.cloudfront.net/public_assets/assets/000/078/685/original/Screenshot_2024-06-19_at_7.17.12_PM.png?1718804854" width=200 /> * If you face any difficulties using this feature, please refer to this video on how to unlock assignments. * <span style=“color:red”>**Note:** The following video is strictly for instructor reference only. [VIDEO LINK](https://www.loom.com/share/15672134598f4b4c93475beda227fb3d?sid=4fb31191-ae8c-4b18-bf81-468d2ffd9bd4)</span> ### Conducting a Live Assignment Solution Session: 1. Once you unlock the assignments, ask if anyone in the class would like to solve a question live by sharing their screen. 2. Select a learner and grant permission by navigating to <span style=“color:skyblue”>**Settings > Admin > Unmuted Audience Can Share**, then select **Audio, Video, and Screen**.</span> <img src="https://d2beiqkhq929f0.cloudfront.net/public_assets/assets/000/111/113/original/image.png?1740484517" width=400 /> 3. Allow the selected learner to share their screen and guide them through solving the question live. 4. Engage with both the learner sharing the screen and other students in the class to foster an interactive learning experience. ### Practice Coding Question(s) You can pick the following question and solve it during the lecture itself. This will help the learners to get familiar with the problem solving process and motivate them to solve the assignments. <span style="background-color: pink;">Make sure to start the doubt session before you solve this question.</span> Q. https://www.scaler.com/hire/test/problem/26837/ - Calculate Age