This commit is contained in:
krahets
2024-05-01 07:30:15 +08:00
parent 85f0bc4ed1
commit d246e08cc6
68 changed files with 220 additions and 220 deletions
@@ -3647,7 +3647,7 @@
<h1 id="34-character-encoding">3.4 &nbsp; Character encoding *<a class="headerlink" href="#34-character-encoding" title="Permanent link">&para;</a></h1>
<p>In the computer system, all data is stored in binary form, and characters (represented by char) are no exception. To represent characters, we need to develop a "character set" that defines a one-to-one mapping between each character and binary numbers. With the character set, computers can convert binary numbers to characters by looking up the table.</p>
<h2 id="341-ascii-character-set">3.4.1 &nbsp; ASCII character set<a class="headerlink" href="#341-ascii-character-set" title="Permanent link">&para;</a></h2>
<p>The "ASCII code" is one of the earliest character sets, officially known as the American Standard Code for Information Interchange. It uses 7 binary digits (the lower 7 bits of a byte) to represent a character, allowing for a maximum of 128 different characters. As shown in the Figure 3-6 , ASCII includes uppercase and lowercase English letters, numbers 0 ~ 9, various punctuation marks, and certain control characters (such as newline and tab).</p>
<p>The "ASCII code" is one of the earliest character sets, officially known as the American Standard Code for Information Interchange. It uses 7 binary digits (the lower 7 bits of a byte) to represent a character, allowing for a maximum of 128 different characters. As shown in Figure 3-6, ASCII includes uppercase and lowercase English letters, numbers 0 ~ 9, various punctuation marks, and certain control characters (such as newline and tab).</p>
<p><a class="glightbox" href="../character_encoding.assets/ascii_table.png" data-type="image" data-width="100%" data-height="auto" data-desc-position="bottom"><img alt="ASCII code" class="animation-figure" src="../character_encoding.assets/ascii_table.png" /></a></p>
<p align="center"> Figure 3-6 &nbsp; ASCII code </p>
@@ -3662,7 +3662,7 @@
<p>"Unicode" is referred to as "统一码" (Unified Code) in Chinese, theoretically capable of accommodating over a million characters. It aims to incorporate characters from all over the world into a single set, providing a universal character set for processing and displaying various languages and reducing the issues of garbled text due to different encoding standards.</p>
<p>Since its release in 1991, Unicode has continually expanded to include new languages and characters. As of September 2022, Unicode contains 149,186 characters, including characters, symbols, and even emojis from various languages. In the vast Unicode character set, commonly used characters occupy 2 bytes, while some rare characters may occupy 3 or even 4 bytes.</p>
<p>Unicode is a universal character set that assigns a number (called a "code point") to each character, <strong>but it does not specify how these character code points should be stored in a computer system</strong>. One might ask: How does a system interpret Unicode code points of varying lengths within a text? For example, given a 2-byte code, how does the system determine if it represents a single 2-byte character or two 1-byte characters?</p>
<p>A straightforward solution to this problem is to store all characters as equal-length encodings. As shown in the Figure 3-7 , each character in "Hello" occupies 1 byte, while each character in "算法" (algorithm) occupies 2 bytes. We could encode all characters in "Hello 算法" as 2 bytes by padding the higher bits with zeros. This method would enable the system to interpret a character every 2 bytes, recovering the content of the phrase.</p>
<p>A straightforward solution to this problem is to store all characters as equal-length encodings. As shown in Figure 3-7, each character in "Hello" occupies 1 byte, while each character in "算法" (algorithm) occupies 2 bytes. We could encode all characters in "Hello 算法" as 2 bytes by padding the higher bits with zeros. This method would enable the system to interpret a character every 2 bytes, recovering the content of the phrase.</p>
<p><a class="glightbox" href="../character_encoding.assets/unicode_hello_algo.png" data-type="image" data-width="100%" data-height="auto" data-desc-position="bottom"><img alt="Unicode encoding example" class="animation-figure" src="../character_encoding.assets/unicode_hello_algo.png" /></a></p>
<p align="center"> Figure 3-7 &nbsp; Unicode encoding example </p>
@@ -3674,7 +3674,7 @@
<li>For 1-byte characters, set the highest bit to <span class="arithmatex">\(0\)</span>, and the remaining 7 bits to the Unicode code point. Notably, ASCII characters occupy the first 128 code points in the Unicode set. This means that <strong>UTF-8 encoding is backward compatible with ASCII</strong>. This implies that UTF-8 can be used to parse ancient ASCII text.</li>
<li>For characters of length <span class="arithmatex">\(n\)</span> bytes (where <span class="arithmatex">\(n &gt; 1\)</span>), set the highest <span class="arithmatex">\(n\)</span> bits of the first byte to <span class="arithmatex">\(1\)</span>, and the <span class="arithmatex">\((n + 1)^{\text{th}}\)</span> bit to <span class="arithmatex">\(0\)</span>; starting from the second byte, set the highest 2 bits of each byte to <span class="arithmatex">\(10\)</span>; the rest of the bits are used to fill the Unicode code point.</li>
</ul>
<p>The Figure 3-8 shows the UTF-8 encoding for "Hello算法". It can be observed that since the highest <span class="arithmatex">\(n\)</span> bits are set to <span class="arithmatex">\(1\)</span>, the system can determine the length of the character as <span class="arithmatex">\(n\)</span> by counting the number of highest bits set to <span class="arithmatex">\(1\)</span>.</p>
<p>Figure 3-8 shows the UTF-8 encoding for "Hello算法". It can be observed that since the highest <span class="arithmatex">\(n\)</span> bits are set to <span class="arithmatex">\(1\)</span>, the system can determine the length of the character as <span class="arithmatex">\(n\)</span> by counting the number of highest bits set to <span class="arithmatex">\(1\)</span>.</p>
<p>But why set the highest 2 bits of the remaining bytes to <span class="arithmatex">\(10\)</span>? Actually, this <span class="arithmatex">\(10\)</span> serves as a kind of checksum. If the system starts parsing text from an incorrect byte, the <span class="arithmatex">\(10\)</span> at the beginning of the byte can help the system quickly detect anomalies.</p>
<p>The reason for using <span class="arithmatex">\(10\)</span> as a checksum is that, under UTF-8 encoding rules, it's impossible for the highest two bits of a character to be <span class="arithmatex">\(10\)</span>. This can be proven by contradiction: If the highest two bits of a character are <span class="arithmatex">\(10\)</span>, it indicates that the character's length is <span class="arithmatex">\(1\)</span>, corresponding to ASCII. However, the highest bit of an ASCII character should be <span class="arithmatex">\(0\)</span>, which contradicts the assumption.</p>
<p><a class="glightbox" href="../character_encoding.assets/utf-8_hello_algo.png" data-type="image" data-width="100%" data-height="auto" data-desc-position="bottom"><img alt="UTF-8 encoding example" class="animation-figure" src="../character_encoding.assets/utf-8_hello_algo.png" /></a></p>
@@ -3594,7 +3594,7 @@
<p>Common data structures include arrays, linked lists, stacks, queues, hash tables, trees, heaps, and graphs. They can be classified into "logical structure" and "physical structure".</p>
<h2 id="311-logical-structure-linear-and-non-linear">3.1.1 &nbsp; Logical structure: linear and non-linear<a class="headerlink" href="#311-logical-structure-linear-and-non-linear" title="Permanent link">&para;</a></h2>
<p><strong>The logical structures reveal the logical relationships between data elements</strong>. In arrays and linked lists, data are arranged in a specific sequence, demonstrating the linear relationship between data; while in trees, data are arranged hierarchically from the top down, showing the derived relationship between "ancestors" and "descendants"; and graphs are composed of nodes and edges, reflecting the intricate network relationship.</p>
<p>As shown in the Figure 3-1 , logical structures can be divided into two major categories: "linear" and "non-linear". Linear structures are more intuitive, indicating data is arranged linearly in logical relationships; non-linear structures, conversely, are arranged non-linearly.</p>
<p>As shown in Figure 3-1, logical structures can be divided into two major categories: "linear" and "non-linear". Linear structures are more intuitive, indicating data is arranged linearly in logical relationships; non-linear structures, conversely, are arranged non-linearly.</p>
<ul>
<li><strong>Linear data structures</strong>: Arrays, Linked Lists, Stacks, Queues, Hash Tables.</li>
<li><strong>Non-linear data structures</strong>: Trees, Heaps, Graphs, Hash Tables.</li>
@@ -3609,8 +3609,8 @@
<li><strong>Network structures</strong>: Graphs, where elements have a many-to-many relationships.</li>
</ul>
<h2 id="312-physical-structure-contiguous-and-dispersed">3.1.2 &nbsp; Physical structure: contiguous and dispersed<a class="headerlink" href="#312-physical-structure-contiguous-and-dispersed" title="Permanent link">&para;</a></h2>
<p><strong>During the execution of an algorithm, the data being processed is stored in memory</strong>. The Figure 3-2 shows a computer memory stick where each black square is a physical memory space. We can think of memory as a vast Excel spreadsheet, with each cell capable of storing a certain amount of data.</p>
<p><strong>The system accesses the data at the target location by means of a memory address</strong>. As shown in the Figure 3-2 , the computer assigns a unique identifier to each cell in the table according to specific rules, ensuring that each memory space has a unique memory address. With these addresses, the program can access the data stored in memory.</p>
<p><strong>During the execution of an algorithm, the data being processed is stored in memory</strong>. Figure 3-2 shows a computer memory stick where each black square is a physical memory space. We can think of memory as a vast Excel spreadsheet, with each cell capable of storing a certain amount of data.</p>
<p><strong>The system accesses the data at the target location by means of a memory address</strong>. As shown in Figure 3-2, the computer assigns a unique identifier to each cell in the table according to specific rules, ensuring that each memory space has a unique memory address. With these addresses, the program can access the data stored in memory.</p>
<p><a class="glightbox" href="../classification_of_data_structure.assets/computer_memory_location.png" data-type="image" data-width="100%" data-height="auto" data-desc-position="bottom"><img alt="Memory stick, memory spaces, memory addresses" class="animation-figure" src="../classification_of_data_structure.assets/computer_memory_location.png" /></a></p>
<p align="center"> Figure 3-2 &nbsp; Memory stick, memory spaces, memory addresses </p>
@@ -3619,7 +3619,7 @@
<p>It's worth noting that comparing memory to an Excel spreadsheet is a simplified analogy. The actual working mechanism of memory is more complex, involving concepts like address space, memory management, cache mechanisms, virtual memory, and physical memory.</p>
</div>
<p>Memory is a shared resource for all programs. When a block of memory is occupied by one program, it cannot be simultaneously used by other programs. <strong>Therefore, considering memory resources is crucial in designing data structures and algorithms</strong>. For instance, the algorithm's peak memory usage should not exceed the remaining free memory of the system; if there is a lack of contiguous memory blocks, then the data structure chosen must be able to be stored in non-contiguous memory blocks.</p>
<p>As illustrated in the Figure 3-3 , <strong>the physical structure reflects the way data is stored in computer memory</strong> and it can be divided into contiguous space storage (arrays) and non-contiguous space storage (linked lists). The two types of physical structures exhibit complementary characteristics in terms of time efficiency and space efficiency.</p>
<p>As illustrated in Figure 3-3, <strong>the physical structure reflects the way data is stored in computer memory</strong> and it can be divided into contiguous space storage (arrays) and non-contiguous space storage (linked lists). The two types of physical structures exhibit complementary characteristics in terms of time efficiency and space efficiency.</p>
<p><a class="glightbox" href="../classification_of_data_structure.assets/classification_phisical_structure.png" data-type="image" data-width="100%" data-height="auto" data-desc-position="bottom"><img alt="Contiguous space storage and dispersed space storage" class="animation-figure" src="../classification_of_data_structure.assets/classification_phisical_structure.png" /></a></p>
<p align="center"> Figure 3-3 &nbsp; Contiguous space storage and dispersed space storage </p>
@@ -3695,7 +3695,7 @@ b_{31} b_{30} b_{29} \ldots b_2 b_1 b_0
\]</div>
<p>Now we can answer the initial question: <strong>The representation of <code>float</code> includes an exponent bit, leading to a much larger range than <code>int</code></strong>. Based on the above calculation, the maximum positive number representable by <code>float</code> is approximately <span class="arithmatex">\(2^{254 - 127} \times (2 - 2^{-23}) \approx 3.4 \times 10^{38}\)</span>, and the minimum negative number is obtained by switching the sign bit.</p>
<p><strong>However, the trade-off for <code>float</code>'s expanded range is a sacrifice in precision</strong>. The integer type <code>int</code> uses all 32 bits to represent the number, with values evenly distributed; but due to the exponent bit, the larger the value of a <code>float</code>, the greater the difference between adjacent numbers.</p>
<p>As shown in the Table 3-2 , exponent bits <span class="arithmatex">\(\mathrm{E} = 0\)</span> and <span class="arithmatex">\(\mathrm{E} = 255\)</span> have special meanings, <strong>used to represent zero, infinity, <span class="arithmatex">\(\mathrm{NaN}\)</span>, etc.</strong></p>
<p>As shown in Table 3-2, exponent bits <span class="arithmatex">\(\mathrm{E} = 0\)</span> and <span class="arithmatex">\(\mathrm{E} = 255\)</span> have special meanings, <strong>used to represent zero, infinity, <span class="arithmatex">\(\mathrm{NaN}\)</span>, etc.</strong></p>
<p align="center"> Table 3-2 &nbsp; Meaning of exponent bits </p>
<div class="center-table">