<jupyter_start><jupyter_text>`list` of `list`'s and references * In Python, one may consider implementing a matrix using a `list` of `list`'s as follows.<jupyter_code>sqrt_2 = 2 ** 0.5
sqrt_3 = 3 ** 0.5
sin_30 = cos_60 = 0.5
sin_60 = cos_30 = 0.5 * sqrt_3

m_rot_30 = [[cos_30, -sin_30],
            [sin_30, cos_30]]

x = [[1.0], [0.0]]

y = [[0.0], [0.0]]
for i in range(2):
    for j in range(1):
        for k in range(2):
            y[i][j] += m_rot_30[i][k] * x[k][j]

print(y)<jupyter_output><empty_output><jupyter_text>* This idea worked. Let's think about preparing for a larger two-dimensional matrix.<jupyter_code>def show_matrix(m, name="matrix_10_by_10"):
    print(f'{name} = ')
    for row in m:
        print(row)
n_row = 10
n_column = 10

# This is one of ways to create a list with n zeros
one_row = [0.0] * n_column
print(f"one_row = {one_row}")

# Let's utilize list * integer here again
matrix_10_by_10 = [one_row] * n_row

show_matrix(matrix_10_by_10)<jupyter_output><empty_output><jupyter_text>* Now let's try to populate the lower triangle part of the matrix.<jupyter_code>def populate_lower_triangle(m):
    for i, row in enumerate(m):
        for j in range(i):
            m[i][j] = j+1.0


populate_lower_triangle(matrix_10_by_10)<jupyter_output><empty_output><jupyter_text>* Now let's take a look<jupyter_code>show_matrix(matrix_10_by_10)<jupyter_output><empty_output><jupyter_text>* What do you think happened?  Approaching differently * This time, let's repeat `[0.0] * n`.<jupyter_code>matrix_10_by_10_new = []

# Repeating [0.0] * n.
for row in range(n_row):

    # a new list
    new_row = [0.0] * n_column

    # append the new row to the matrix
    matrix_10_by_10_new.append(new_row)

show_matrix(matrix_10_by_10_new, 'matrix_10_by_10_new')


populate_lower_triangle(matrix_10_by_10_new)
show_matrix(matrix_10_by_10_new)<jupyter_output><empty_output><jupyter_text>* Why the result is different this time?  `is` operator and `id()` function * Observe the following code blocks. * What would be the role of the `is` operator here?* How can we use `id()` function?<jupyter_code>print("matrix_10_by_10[0] =")
print(matrix_10_by_10[0])

print("matrix_10_by_10[1] =")
print(matrix_10_by_10[1])

# An assignment operation to matrix_10_by_10[0]
matrix_10_by_10[0][0] = 'z'
print("matrix_10_by_10[0][0] = 'z'")

print("matrix_10_by_10[0] =")
print(matrix_10_by_10[0])

print("matrix_10_by_10[1] =")
print(matrix_10_by_10[1])

print("matrix_10_by_10[0] is matrix_10_by_10[1] =")
print(matrix_10_by_10[0] is matrix_10_by_10[1])

for i in range(10):
    print(f"hex(id(matrix_10_by_10[{i}])) = {hex(id(matrix_10_by_10[i]))}")


print("matrix_10_by_10_new[0] =")
print(matrix_10_by_10_new[0])

print("matrix_10_by_10_new[1] =")
print(matrix_10_by_10_new[1])

# An assignment operation to matrix_10_by_10_new[0]
matrix_10_by_10_new[0][0] = 'z'
print("matrix_10_by_10_new[0][0] = 'z'")

print("matrix_10_by_10_new[0] =")
print(matrix_10_by_10_new[0])

print("matrix_10_by_10_new[1] =")
print(matrix_10_by_10_new[1])

print("matrix_10_by_10_new[0] is matrix_10_by_10_new[1] =")
print(matrix_10_by_10_new[0] is matrix_10_by_10_new[1])

for i in range(10):
    print(f"hex(id(matrix_10_by_10_new[{i}])) = {hex(id(matrix_10_by_10_new[i]))}")<jupyter_output><empty_output>
{'fraction_non_alphanumeric': 0.1452887537993921, 'fraction_numerical': 0.08389057750759879, 'mean_word_length': 5.85625, 'pattern_counts': {'":': 0, '<': 25, '<?xml version=': 0, '>': 25, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'chain_length': '6', 'dir': 'jupyter-structured-clean-dedup', 'id': '272521', 'license': 'BSD-3-Clause', 'n_tokens_mistral': 1541, 'n_tokens_neox': 1403, 'n_words': 268, 'path': '02.ipynb', 'repo_name': '2018pycpp/18pycpp-03', 'size': '3290'}