Q1. Scenario: Create a 1D array of 10 numbers from 0 to 9. Extract the first 3 elements, the last 2 elements, and every 2nd element starting from index 2.
arr = np.arange(10); first3 = arr[:3]; last2 = arr[-2:]; step2 = arr[2::2]. Output: [0,1,2]; [8,9]; [2,4,6,8]. Slicing uses start:stop:step. Negative indices count from end.
Q2. Scenario: You have a 2D array (3 rows, 4 columns). Select the second row, the third column, and the submatrix consisting of rows 0-1 and columns 1-3.
arr = np.arange(12).reshape(3,4); row1 = arr[1,:]; col2 = arr[:,2]; sub = arr[0:2, 1:4]. Manual: row1 = [4,5,6,7]; col2 = [2,6,10]; sub = [[1,2,3],[5,6,7]]. Comma separates row and column indices.
Q3. Scenario: Using boolean indexing, select all elements greater than 5 from array [1,6,2,7,3,8,4,9]. Then replace all elements less than 5 with 0.
arr = np.array([1,6,2,7,3,8,4,9]); gt5 = arr[arr > 5] -> [6,7,8,9]; arr[arr < 5] = 0 -> [0,6,0,7,0,8,0,9]. Boolean indexing is powerful for filtering and conditional assignment.
Q4. Scenario: You have a 5x5 identity matrix. Use fancy indexing to set the first and third rows to zeros. Then set the last column to 5.
eye = np.eye(5); eye[[0,2], :] = 0; eye[:, -1] = 5. Fancy indexing uses integer lists. Result: rows 0 and 2 become zeros; last column all 5s.
Q5. Scenario: Given a 2D array of shape (4,4), extract the diagonal elements using two methods: diagonal() and fancy indexing.
arr = np.arange(16).reshape(4,4); diag = np.diagonal(arr); fancy = arr[np.arange(4), np.arange(4)]. Both yield [0,5,10,15]. np.diag(arr) also gives diagonal. Used for trace and extracting parameters.
