

<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>MaxCodeReview</title>
	<atom:link href="https://codereview.max-everyday.com/feed/" rel="self" type="application/rss+xml" />
	<link>https://codereview.max-everyday.com</link>
	<description>分享Max收集的小程式</description>
	<lastBuildDate>Mon, 19 Jan 2026 19:35:33 +0000</lastBuildDate>
	<language>zh-TW</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=6.9.1</generator>

<image>
	<url>https://codereview.max-everyday.com/wp-content/uploads/2020/07/cropped-logo1_x512-32x32.jpg</url>
	<title>MaxCodeReview</title>
	<link>https://codereview.max-everyday.com</link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>TTF 轉 WOFF2 工具</title>
		<link>https://codereview.max-everyday.com/ttf-to-woff2/</link>
		
		<dc:creator><![CDATA[max-code-review-usr1]]></dc:creator>
		<pubDate>Mon, 19 Jan 2026 18:50:42 +0000</pubDate>
				<category><![CDATA[字體]]></category>
		<category><![CDATA[Font]]></category>
		<category><![CDATA[Python]]></category>
		<guid isPermaLink="false">https://codereview.max-everyday.com/?p=2143</guid>

					<description><![CDATA[除了 FontForge 之外，目前市場上有 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>除了 FontForge 之外，目前市場上有許多更現代且易於使用的 TTF 轉 WOFF2 工具，分別適合網頁開發者、設計師或是有大量轉換需求的工程師。</p>



<h2 class="wp-block-heading">線上轉換工具</h2>



<p>如果你不想安裝軟體，且轉換數量不多，這幾個網站是首選。</p>



<ul class="wp-block-list">
<li>Fontsource Webfont Converter純瀏覽器處理，檔案不會上傳到伺服器，對隱私更有保障，速度也非常快。</li>



<li>Transfonter這是目前開發者最推薦的工具。它除了轉換格式，還能幫你生成 @font-face 的 CSS 代碼，並支援字體子集化（Subsetting）來縮減檔案體積。</li>



<li>CloudConvert萬用型的檔案轉換器，如果你的字體檔案非常大（超過 10MB），一般的網頁工具可能會失敗，這時可以用 CloudConvert 處理。</li>
</ul>



<h2 class="wp-block-heading">命令列工具 (CLI)</h2>



<p>如果你需要批次處理，或是想把轉換流程加入自動化腳本，這幾個工具非常強大。</p>



<ul class="wp-block-list">
<li>google/woff2這是 Google 官方釋出的參考代碼。在 macOS 可以直接用 brew install woff2 安裝，之後在終端機輸入 <br>woff2_compress yourfont.ttf <br>就能得到 WOFF2 檔。</li>



<li>fonttools (Python)這是字體工程領域的標準工具。安裝 Python 後執行 <br>pip install fonttools<br>轉換指令：<br>pyftsubset yourfont.ttf &#8220;*&#8221; &#8211;flavor=woff2 &#8211;output-file=yourfont.woff2</li>



<li>wawoff2 (Node.js)這是 Google woff2 的 WebAssembly 版本，適合 Node.js 環境。執行 <br>npx wawoff2 compress yourfont.ttf</li>
</ul>



<h2 class="wp-block-heading">工具對比總結</h2>



<figure class="wp-block-table"><table class="has-fixed-layout"><thead><tr><td><strong>工具類型</strong></td><td><strong>推薦名稱</strong></td><td><strong>優點</strong></td><td><strong>缺點</strong></td></tr></thead><tbody><tr><td>線上網頁</td><td>Transfonter</td><td>功能最全，可生成 CSS</td><td>有檔案大小限制</td></tr><tr><td>線上網頁</td><td>Fontsource</td><td>本地瀏覽器運算，隱私好</td><td>功能較單一</td></tr><tr><td>命令列 (C++)</td><td>woff2 (Google)</td><td>速度最快，官方標準</td><td>需手動編譯或安裝環境</td></tr><tr><td>命令列 (Python)</td><td>fonttools</td><td>功能最強大，支援子集化</td><td>學習曲線較高</td></tr></tbody></table></figure>



<p>如果你只需要簡單轉檔給網站用，我建議直接用 Transfonter。如果你是想研究如何縮小字體體積，那麼 fonttools 是比較專業的選擇。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">使用 Python 進行自動化轉換</h2>



<p>如果你的電腦有安裝 Python，使用 fonttools 是最專業的做法。它不只能轉檔，還能移除字體中用不到的字元來減肥。</p>



<p>首先安裝必要的套件：</p>



<pre class="wp-block-code"><code>pip install fonttools brotli
</code></pre>



<p>接著你可以使用這段簡單的腳本，它會掃描資料夾內所有的 TTF 檔案並轉換成 WOFF2：</p>



<pre class="wp-block-code"><code>import os
from fontTools.ttLib import TTFont

def convert_to_woff2():
    for file in os.listdir('.'):
        if file.endswith('.ttf'):
            font = TTFont(file)
            output_name = file.replace('.ttf', '.woff2')
            font.save(output_name, reorderTables=True)
            print(f'已完成: {output_name}')

if __name__ == '__main__':
    convert_to_woff2()
</code></pre>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">使用 Shell 指令批次轉換</h2>



<p>如果你在 macOS 或 Linux 環境，且已經安裝 Google 官方的 woff2 工具，可以用一行指令處理整個資料夾。</p>



<p>安裝方式：</p>



<pre class="wp-block-code"><code>brew install woff2
</code></pre>



<p>轉換指令：</p>



<pre class="wp-block-code"><code>for f in *.ttf; do woff2_compress "$f"; done
</code></pre>



<p>這會直接在同個資料夾產生對應的 WOFF2 檔案。這個工具的壓縮率通常是最好的，因為它使用了 Google 開發的 Brotli 壓縮演算法。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<p>pyftsubset 是 fonttools 套件中最強大的工具。它的核心邏輯是從原始字體中「切出」你需要的部分，並重新打包成網頁專用的格式。</p>



<h3 class="wp-block-heading">基礎轉換指令</h3>



<p>如果你不需要刪除任何字元，只是單純想把 TTF 轉成 WOFF2，可以使用這個指令。</p>



<p>Bash</p>



<pre class="wp-block-code"><code>pyftsubset input.ttf --glyphs="*" --flavor=woff2 --output-file=output.woff2
</code></pre>



<ul class="wp-block-list">
<li><code>--glyphs="*"</code>：代表保留原字體中所有的字元，不進行刪減。</li>



<li><code>--flavor=woff2</code>：指定輸出格式為 WOFF2。如果不加這行，預設會輸出 TTF。</li>
</ul>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">字體子集化（縮減體積）</h3>



<p>中文字體動輒 10MB 以上，載入速度很慢。子集化可以讓你只保留網頁會用到的字。</p>



<ul class="wp-block-list">
<li>指定文字內容：如果你只想保留特定的字（例如「你好」），可以使用 &#8211;text。Bash<code>pyftsubset input.ttf --text="你好" --flavor=woff2</code></li>



<li>使用 Unicode 範圍：如果你想保留常用的中文字範圍，可以使用 &#8211;unicodes。Bash<code>pyftsubset input.ttf --unicodes="U+4E00-9FFF" --flavor=woff2</code></li>
</ul>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">常用的進階參數</h3>



<p>為了讓網頁載入更順暢，建議加上以下參數優化字體結構。</p>



<ul class="wp-block-list">
<li>&#8211;layout-features=&#8221;*&#8221;預設情況下，子集化會刪除 OpenType 特性（如連字、垂直排版）。如果你需要保留這些功能，務必加上這個參數。</li>



<li>&#8211;no-hinting如果你不在意舊螢幕的清晰度，移除 Hinting 資訊可以再減少約 10% 到 20% 的檔案大小。</li>



<li>&#8211;desubroutinize針對 CJK（中日韓）字體，這可以解決某些瀏覽器在渲染子集化後的 CJK 字體時出現的異常。</li>
</ul>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">完整的專業指令推薦</h3>



<p>這是我最常建議的「高效能網頁字體」轉換公式：</p>



<pre class="wp-block-code"><code>pyftsubset MarukoGothic.ttf --unicodes="U+4E00-9FFF,U+0000-007F" --flavor=woff2 --layout-features="*" --output-file=font.woff2
</code></pre>



<p>這個指令會保留「基本拉丁字母」與「常用中文字範圍」，並維持所有的字體排版特性。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<p>針對你的需求，要把日文、英文以及常用標點符號都包進去，你需要組合多個 Unicode 區塊。</p>



<h3 class="wp-block-heading">推薦的 Unicode 範圍組合</h3>



<p>你可以將以下這段字串直接複製到 <code>--unicodes</code> 參數後。這包含了基本英文、常用符號、日文（平假名、片假名、漢字）以及中文字：</p>



<pre class="wp-block-code"><code>U+0000-007F,U+00A0-00FF,U+2000-206F,U+3000-303F,U+3040-309F,U+30A0-30FF,U+4E00-9FFF,U+FF00-FFEF
</code></pre>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">各區塊詳細說明</h3>



<p>下表拆解了這串代碼代表的意義，你可以根據需求增減：</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><thead><tr><td><strong>範圍 (Unicode Range)</strong></td><td><strong>內容說明</strong></td><td><strong>包含項目</strong></td></tr></thead><tbody><tr><td><strong>U+0000-007F</strong></td><td>基本拉丁字母</td><td>數字、大小寫英文字母、基礎半形標點</td></tr><tr><td><strong>U+00A0-00FF</strong></td><td>拉丁增補</td><td>西歐語言常用符號、貨幣符號</td></tr><tr><td><strong>U+2000-206F</strong></td><td>一般標點</td><td>特殊引號、破折號、點號</td></tr><tr><td><strong>U+3000-303F</strong></td><td>CJK 符號</td><td>全形空格、句號、括號、頓號</td></tr><tr><td><strong>U+3040-309F</strong></td><td>平假名</td><td>日文平假名、濁音符號</td></tr><tr><td><strong>U+30A0-30FF</strong></td><td>片假名</td><td>日文片假名、長音符號</td></tr><tr><td><strong>U+4E00-9FFF</strong></td><td>CJK 漢字</td><td>常用繁體、簡體、日文漢字</td></tr><tr><td><strong>U+FF00-FFEF</strong></td><td>半形/全形形式</td><td>全形英文字母、全形數字、常用符號</td></tr></tbody></table></figure>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">最終執行指令範例</h3>



<p>這是一個非常完整的轉換指令，適合處理像「丸子黑體」這類包含中日文的字體：</p>



<p>for macOS / Linux:</p>



<pre class="wp-block-code"><code>pyftsubset MarukoGothic.ttf \
--unicodes="U+0000-007F,U+00A0-00FF,U+2000-206F,U+3000-303F,U+3040-309F,U+30A0-30FF,U+4E00-9FFF,U+FF00-FFEF" \
--flavor=woff2 \
--layout-features="*" \
--output-file=MarukoGothic_optimized.woff2
</code></pre>



<p>for Windows:</p>



<pre class="wp-block-code"><code>pyftsubset MarukoGothic.ttf ^
--unicodes="U+0000-007F,U+00A0-00FF,U+2000-206F,U+3000-303F,U+3040-309F,U+30A0-30FF,U+4E00-9FFF,U+FF00-FFEF" ^
--flavor=woff2 ^
--layout-features="*" ^
--output-file=MarukoGothic_optimized.woff2</code></pre>



<h3 class="wp-block-heading">小提醒</h3>



<p>如果你發現某些特殊的避頭尾點號（如雙引號）沒出現，通常是因為它們落在 <code>U+2018-201D</code> 之間，上面的 <code>U+2000-206F</code> 已經完整覆蓋了。</p>



<p></p>



<p></p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>tail 顯示末幾行</title>
		<link>https://codereview.max-everyday.com/tail/</link>
		
		<dc:creator><![CDATA[max-code-review-usr1]]></dc:creator>
		<pubDate>Thu, 01 Jan 2026 18:23:16 +0000</pubDate>
				<category><![CDATA[Python]]></category>
		<guid isPermaLink="false">https://codereview.max-everyday.com/?p=2113</guid>

					<description><![CDATA[為什麼需要這個程式 處理大型檔案的時候，如果 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<h2 class="wp-block-heading">為什麼需要這個程式</h2>



<p>處理大型檔案的時候，如果一次把整份檔案讀進記憶體，電腦很容易當機。這段程式碼實現了類似 Linux 系統中 tail 指令的功能。它能讓你只讀取檔案最後面幾行文字。這在檢查伺服器紀錄或大型數據檔案時非常方便。開發者不需要載入整份文件就能快速看到最新的訊息。</p>



<h2 class="wp-block-heading">如何開始使用</h2>



<p>下載程式碼：<br><a href="https://github.com/max32002/MaxFontScripts/blob/master/tail.py">https://github.com/max32002/MaxFontScripts/blob/master/tail.py</a></p>



<p>確保你的電腦已經安裝了 Python 3 環境。你可以透過終端機或命令提示字元來執行它。</p>



<h2 class="wp-block-heading">基本指令格式</h2>



<pre class="wp-block-code"><code><code>python <span style="background-color: initial; font-family: inherit; text-align: initial;">tail</span><span style="background-color: rgba(71, 66, 93, 0.2); font-family: inherit; text-align: initial;">.py </span><span style="font-family: inherit; text-align: initial; background-color: initial;">file</span><span style="background-color: rgba(71, 66, 93, 0.2); font-family: inherit; text-align: initial;"> </span><span style="font-family: inherit; text-align: initial; background-color: initial;">lines</span></code></code></pre>



<p>第一個位置參數是 file，代表你要讀取的目標檔案路徑。</p>



<p>第二個位置參數是 lines，代表你想從末尾讀取幾行。</p>



<p>最後還有一個選用參數 -o 或 &#8211;output。如果你加上這個參數，程式會將結果存入你指定的檔案。</p>



<h2 class="wp-block-heading">實際使用範例</h2>



<p>如果你想直接在螢幕上查看最後 10 行內容，可以輸入：</p>



<pre class="wp-block-code"><code>python tail.py log.txt 10
</code></pre>



<p>如果你想把最後 50 行的內容存成一個新檔案 result.txt，可以輸入：</p>



<pre class="wp-block-code"><code>python tail.py log.txt 50 -o result.txt
</code></pre>



<p>這樣就能快速完成檔案的擷取。即使檔案大小有數個 GB 也能瞬間完成。</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>head 顯示前幾行</title>
		<link>https://codereview.max-everyday.com/head/</link>
		
		<dc:creator><![CDATA[max-code-review-usr1]]></dc:creator>
		<pubDate>Thu, 01 Jan 2026 18:21:14 +0000</pubDate>
				<category><![CDATA[Python]]></category>
		<category><![CDATA[字串處理]]></category>
		<guid isPermaLink="false">https://codereview.max-everyday.com/?p=2109</guid>

					<description><![CDATA[為什麼需要這個程式 處理大型檔案的時候，如果 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<h2 class="wp-block-heading">為什麼需要這個程式</h2>



<p>處理大型檔案的時候，如果一次把整份檔案讀進記憶體，電腦很容易當機。這段程式碼實現了類似 Linux 系統中 head 指令的功能。它能讓你只讀取檔案最前面幾行文字。這在檢查伺服器紀錄或大型數據檔案時非常方便。</p>



<h2 class="wp-block-heading">如何開始使用</h2>



<p>下載程式碼：<br><a href="https://github.com/max32002/MaxFontScripts/blob/master/head.py">https://github.com/max32002/MaxFontScripts/blob/master/head.py</a></p>



<p>確保你的電腦已經安裝了 Python 3 環境。你可以透過終端機或命令提示字元來執行它。</p>



<h2 class="wp-block-heading">基本指令格式</h2>



<pre class="wp-block-code"><code><code>python head.py <span style="background-color: initial; font-family: inherit; text-align: initial;">file</span> <span style="background-color: initial; font-family: inherit; text-align: initial;">lines</span></code></code></pre>



<p>第一個位置參數是 file，代表你要讀取的目標檔案路徑。</p>



<p>第二個位置參數是 lines，代表你想從最前讀取幾行。</p>



<p>最後還有一個選用參數 -o 或 &#8211;output。如果你加上這個參數，程式會將結果存入你指定的檔案。</p>



<h2 class="wp-block-heading">實際使用範例</h2>



<p>如果你想直接在螢幕上查看最前 10 行內容，可以輸入：</p>



<pre class="wp-block-code"><code>python head.py log.txt 10
</code></pre>



<p>如果你想把最前 50 行的內容存成一個新檔案 result.txt，可以輸入：</p>



<pre class="wp-block-code"><code>python head.py log.txt 50 -o result.txt
</code></pre>



<p>這樣就能快速完成檔案的擷取。即使檔案大小有數個 GB 也能瞬間完成。</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>grep 查詢文字檔內容</title>
		<link>https://codereview.max-everyday.com/grep/</link>
		
		<dc:creator><![CDATA[max-code-review-usr1]]></dc:creator>
		<pubDate>Thu, 01 Jan 2026 18:14:25 +0000</pubDate>
				<category><![CDATA[字串處理]]></category>
		<guid isPermaLink="false">https://codereview.max-everyday.com/?p=2105</guid>

					<description><![CDATA[平常寫程式或做作業常要翻 log 檔案。檔案 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>平常寫程式或做作業常要翻 log 檔案。檔案太大時根本看不完。這段 Python 腳本可以幫上忙。它像是一個客製化的 grep 工具。支援關鍵字高亮顯示。還能決定要看關鍵字前後幾行內容。這對分析程式報錯很有幫助。</p>



<h2 class="wp-block-heading">如何開始使用</h2>



<p>下載程式碼：<br><a href="https://github.com/max32002/MaxFontScripts/blob/master/grep.py">https://github.com/max32002/MaxFontScripts/blob/master/grep.py</a></p>



<p>確保你的電腦已經安裝了 Python 3 環境。你可以透過終端機或命令提示字元來執行它。</p>



<h2 class="wp-block-heading">基本指令格式</h2>



<pre class="wp-block-code"><code>python grep.py 關鍵字 路徑</code></pre>



<p>你可以加上這些參數：</p>



<ul class="wp-block-list">
<li>-b 數字：顯示關鍵字前面幾行。</li>



<li>-a 數字：顯示關鍵字後面幾行。</li>



<li>-i：忽略英文字母大小寫。</li>



<li>-l：把找到的關鍵字標上顏色。</li>



<li>-E：開啟正規表示法搜尋模式。</li>



<li>-ext .txt：搜尋指定副檔名。</li>



<li>-o 檔名：將搜尋結果存成檔案。</li>



<li>-r or -R：預設只會掃描該層資料夾，除非你加上 -r 才會遞迴搜尋子目錄。</li>
</ul>



<h2 class="wp-block-heading">實際操作範例</h2>



<p>假設要找 logs 資料夾內所有包含 ERROR 的行。並且要看錯誤發生的前 2 行與後 2 行。還要標記顏色。</p>



<pre class="wp-block-code"><code>python grep.py ERROR ./logs -b 2 -a 2 -l
</code></pre>



<p>如果要用正規表示法找特定格式。例如找 IP 位址。並限制只找 .txt 檔案。</p>



<pre class="wp-block-code"><code>python grep.py "&#91;0-9]+\.&#91;0-9]+\.&#91;0-9]+\.&#91;0-9]+" ./data -E -ext .txt
</code></pre>



<p>如果想把搜尋結果存起來。方便之後寫報告用。</p>



<pre class="wp-block-code"><code>python grep.py "Login Failed" auth.log -o result.txt
</code></pre>



<p>這套工具邏輯很單純。不用安裝複雜的套件。做實驗數據分析或是 debug 都很實用。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<p>正規表示式（Regular Expression）在處理文字時非常強大。以下整理了最常用的規則與符號，不論是在 Python、JavaScript 或是終端機工具都通用。</p>



<h3 class="wp-block-heading">基本字元與邊界</h3>



<p>這些符號用來定位文字的位置或是匹配特定類型的單一字元。</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><thead><tr><td><strong>符號</strong></td><td><strong>說明</strong></td><td><strong>範例</strong></td></tr></thead><tbody><tr><td><strong>.</strong></td><td>匹配除換行符號外的任何單一字元</td><td><code>a.c</code> 可匹配 abc, a2c</td></tr><tr><td><strong>^</strong></td><td>匹配字串的開頭</td><td><code>^Hello</code> 必須以 Hello 開頭</td></tr><tr><td><strong>$</strong></td><td>匹配字串的結尾</td><td><code>done$</code> 必須以 done 結尾</td></tr><tr><td><strong>\d</strong></td><td>匹配任何數字，等同於 [0-9]</td><td><code>\d\d</code> 匹配兩位數</td></tr><tr><td><strong>\D</strong></td><td>匹配任何非數字字元</td><td><code>\D</code> 匹配字母或符號</td></tr><tr><td><strong>\w</strong></td><td>匹配字母、數字或底線</td><td><code>\w+</code> 匹配一個單字</td></tr><tr><td><strong>\s</strong></td><td>匹配任何空白字元（空格、Tab、換行）</td><td><code>\s+</code> 匹配連續空白</td></tr><tr><td><strong>\b</strong></td><td>匹配單字邊界</td><td><code>\bcat\b</code> 只匹配 cat 不含 category</td></tr></tbody></table></figure>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">量詞（次數匹配）</h3>



<p>用來決定前面的字元可以連續出現幾次。</p>



<ul class="wp-block-list">
<li><strong>*</strong>：出現 0 次或多次。</li>



<li><strong>+</strong>：出現 1 次或多次（至少要有一個）。</li>



<li><strong>?</strong>：出現 0 次或 1 次（選用性質）。</li>



<li><strong>{n}</strong>：精確出現 n 次。</li>



<li><strong>{n,}</strong>：出現至少 n 次。</li>



<li><strong>{n,m}</strong>：出現 n 到 m 次之間。</li>
</ul>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">字元集合與群組</h3>



<p>當你需要指定一段範圍或是將多個規則組合在一起時。</p>



<ul class="wp-block-list">
<li><strong>[abc]</strong>：匹配括號內的任一字元。</li>



<li><strong>[^abc]</strong>：匹配除了 abc 以外的任何字元。</li>



<li><strong>[a-z]</strong>：匹配小寫字母 A 到 Z。</li>



<li><strong>[A-Z]</strong>：匹配大寫字母 A 到 Z。</li>



<li><strong>|</strong>：邏輯「或」（OR），例如 <code>cat|dog</code> 匹配 cat 或 dog。</li>



<li><strong>(&#8230;)</strong>：擷取群組，將規則組合在一起，之後可以用 <code>\1</code> 或在程式中提取。</li>



<li><strong>(?:&#8230;)</strong>：非擷取群組，只組合不記錄內容，效能較好。</li>
</ul>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">貪婪與懶惰匹配</h3>



<p>這是進階使用時最常遇到的陷阱。</p>



<p>預設情況下，量詞是「貪婪的」，會盡可能匹配最長的字串。例如對於 <code>&lt;div&gt;test&lt;/div&gt;</code> 使用 <code>&lt;.*&gt;</code> 會匹配到整個字串。</p>



<p>如果在量詞後面加上問號（例如 <code>*?</code> 或 <code>+?</code>），會變成「懶惰模式」，只匹配到第一個符合條件的結尾。例如 <code>&lt;.*?&gt;</code> 只會匹配到 <code>&lt;div&gt;</code>。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h3 class="wp-block-heading">實戰小筆記</h3>



<p>在撰寫規則時，如果遇到特殊符號如 <code>.</code>、<code>*</code>、<code>?</code>、<code>(</code> 等，必須在前面加上反斜線 <code>\</code> 進行跳脫，才能匹配符號本身。</p>



<p>例如要匹配一個 IP 地址，簡單的寫法會是：<code>\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}</code>。</p>



<p>你想看如何將這些規則應用在你之前的 versionName 修改腳本中嗎？</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<p>非擷取群組 <code>(?:...)</code> 的主要作用是「只組合、不存檔」。它讓你可以對一組字元進行量詞操作，但不會在記憶體中記錄這個群組的內容，這在處理複雜字串或提升效能時很有用。</p>



<h3 class="wp-block-heading">範例一：純粹為了使用量詞</h3>



<p>如果你想匹配「連續出現多次的單字」，但你只關心整個字串，不需要單獨取出那個單字。</p>



<ul class="wp-block-list">
<li><strong>正規表示式</strong>：<code>^(?:https?|ftp)://[^\s]+$</code></li>



<li><strong>說明</strong>：這裡用 <code>(?:https?|ftp)</code> 把通訊協定組合起來，後面加個 <code>|</code> 代表「或」。如果你用 <code>(https?|ftp)</code>，程式會額外幫你存下一個變數（Group 1）記錄到底是匹配到 http 還是 ftp。用非擷取群組則可以省去這個開銷。</li>
</ul>



<h3 class="wp-block-heading">範例二：搭配擷取群組使用</h3>



<p>當你的正規表示式很長，裡面有很多層括號，使用非擷取群組可以讓你的「編號」更乾淨。</p>



<ul class="wp-block-list">
<li><strong>待處理文字</strong>：<code>ID: 123-ABC, ID: 456-DEF</code></li>



<li><strong>正規表示式</strong>：<code>ID: (\d+)-(?:[A-Z]+)</code></li>



<li><strong>程式結果</strong>：
<ul class="wp-block-list">
<li><code>Group 1</code> 會拿到 <code>123</code>。</li>



<li>因為 <code>[A-Z]+</code> 放在 <code>(?:...)</code> 裡面，它不會被分配到 <code>Group 2</code>。</li>



<li>這在寫程式時，可以避免去算到底現在是第幾個括號。</li>
</ul>
</li>
</ul>



<h3 class="wp-block-heading">範例三：在分割字串時的差異 (以 Python 為例)</h3>



<p>這是在實作中最明顯的區別。</p>



<p>Python</p>



<pre class="wp-block-code"><code>import re

text = "apple123orange456banana"

# 使用一般群組：分隔符號會被保留在結果清單中
print(re.split(r"(\d+)", text)) 
# 輸出: &#91;'apple', '123', 'orange', '456', 'banana']

# 使用非擷取群組：分隔符號會被丟棄，只留下分割後的內容
print(re.split(r"(?:\d+)", text)) 
# 輸出: &#91;'apple', 'orange', 'banana']
</code></pre>



<h3 class="wp-block-heading">總結建議</h3>



<p>當你發現括號只是為了「要把這幾個字看成一體」或是「為了用 OR 邏輯」，而不是為了之後要把這段文字抽出來用時，就應該習慣加上 <code>?:</code>。這不僅能讓程式跑得快一點，也能讓後續維護程式碼的人（或你自己）知道，這一段內容不需要被抓取。</p>



<p></p>



<p></p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>檔案內容的字串取代</title>
		<link>https://codereview.max-everyday.com/replace-string/</link>
		
		<dc:creator><![CDATA[max-code-review-usr1]]></dc:creator>
		<pubDate>Wed, 31 Dec 2025 08:36:07 +0000</pubDate>
				<category><![CDATA[Python]]></category>
		<category><![CDATA[字串處理]]></category>
		<guid isPermaLink="false">https://codereview.max-everyday.com/?p=2076</guid>

					<description><![CDATA[為什麼需要這段程式碼 手動修改幾十個檔案的內 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<h2 class="wp-block-heading">為什麼需要這段程式碼</h2>



<p>手動修改幾十個檔案的內容很累。如果只是改一個字還好，但如果要改符合特定規則的文字，手動操作幾乎不可能。這段 Python 腳本就是為了解決這個問題。它能幫你快速搜尋資料夾，找到符合條件的檔案，並用正則表達式進行批次替換。這對處理程式碼版本號、路徑更新或大量文件修改非常有用。</p>



<h2 class="wp-block-heading">如何開始使用</h2>



<p>下載程式碼：<br><a href="https://github.com/max32002/MaxFontScripts/blob/master/replace_string.py">https://github.com/max32002/MaxFontScripts/blob/master/replace_string.py</a></p>



<p>確保你的電腦已經安裝了 Python 3 環境。你可以透過終端機或命令提示字元來執行它。</p>



<h2 class="wp-block-heading">基本的文字替換</h2>



<p>最簡單的用法是直接替換特定的單字。如果你有一個資料夾叫做 docs，裡面有很多文件要把 Apple 改成 Orange，你可以輸入指令。</p>



<pre class="wp-block-code"><code>python replace_string.py ./docs "Apple" "Orange"
</code></pre>



<p>這會掃描 docs 資料夾下的所有檔案。只要看到 Apple 就會換成 Orange。程式會自動過濾無法開啟的檔案。修改成功的檔案會顯示在畫面上。</p>



<h2 class="wp-block-heading">進階的參數</h2>



<p>-r or -R：預設只會掃描該層資料夾，除非你加上 -r 才會遞迴搜尋子目錄。</p>



<h2 class="wp-block-heading">使用正則表達式處理複雜規則</h2>



<p>這段腳本強大的地方在於支援正則表達式。假設你有很多設定檔，裡面的版本號可能是 v1.0 或 v2.5。你想把所有 v 開頭加上數字的版本號都統一改成 v3。你可以利用正則表達式的符號。</p>



<pre class="wp-block-code"><code>python replace_string.py ./project "v\d+" "v3"
</code></pre>



<p>這裡的 v\d+ 代表一個 v 後面接一個以上的數字。這比單純的關鍵字搜尋更靈活。它能一次處理所有符合規則的變動。</p>



<h2 class="wp-block-heading">指定特定的檔案類型</h2>



<p>有時候你不想動到資料夾裡的所有檔案。例如你只想修改副檔名是 .conf 的設定檔。這時候可以在指令最後面加上過濾條件。</p>



<pre class="wp-block-code"><code>python replace_string.py ./config "127.0.0.1" "0.0.0.0" "*.conf"
</code></pre>



<p>這樣腳本就只會檢查 .conf 結尾的檔案。這能避免誤動到圖片或執行檔。這對保護專案中的其他檔案非常安全。</p>



<h2 class="wp-block-heading">運作原理與安全機制</h2>



<p>腳本在修改時會先建立一個暫存檔。它會逐行讀取原檔案，處理完後寫入暫存檔。如果內容真的有變動，才會取代舊檔案。如果內容完全一樣，就會刪除暫存檔。這種做法能防止程式執行到一半出錯，導致原本的檔案損毀。</p>



<h2 class="wp-block-heading">使用前的小提醒</h2>



<p>雖然腳本有安全機制，但批次修改依然有風險。建議在執行大量替換前，先備份你的資料夾。你可以先拿一個小檔案做測試。確認正則表達式的結果符合預期後，再對整個專案執行。這是一個好習慣。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<p>想試試看對特定目錄下的所有 Markdown 檔案進行標題格式轉換嗎？</p>



<h2 class="wp-block-heading">實戰演練調整標題層級</h2>



<p>假設你寫了很多筆記，但發現一級標題太大了。你想把所有 Markdown 檔案的一級標題改成二級標題。這在整理文件架構時非常有幫助。手動改一百個檔案會耗費太多時間。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">具體的執行指令</h2>



<p>你可以使用正則表達式來精確定位標題。開啟終端機並切換到腳本所在的目錄。輸入下面的指令。</p>



<pre class="wp-block-code"><code>python replace_string.py ./my_notes "^#\s" "## " "*.md"
</code></pre>



<p>這裡的 <code>^#\s</code> 是關鍵。<code>^</code> 代表每一行的開頭。<code>#</code> 是我們要找的符號。<code>\s</code> 代表空白鍵。這樣可以確保只會改到真正的標題。它不會動到內文中間出現的井字號。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">執行後的結果</h2>



<p>程式會掃描 my_notes 資料夾下所有的 .md 檔案。它會把每一行開頭的井字號多加一個。處理完後你會看到螢幕顯示哪些檔案已經被修改。如果檔案裡面沒有符合條件的內容，程式會顯示無變動。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">檢查與備份</h2>



<p>在執行這類批次修改前，建議先備份資料夾。你可以先複製一份複本出來。或者先對單一檔案執行測試。確認轉換邏輯完全正確。這能避免正則表達式寫錯導致檔案內容亂掉。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">正則表達式的基本邏輯</h2>



<p>正則表達式其實就是一種文字的「特徵描述」。它用一串特殊的符號，來描述文字長什麼樣子。這在處理大量文件時超級好用。你可以把它想像成一種進階版的搜尋功能。以下整理了最常用的幾組符號。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">基礎匹配符號</h2>



<p>這些符號用來代表單一個字元或是位置。它們是所有正則表達式的根基。</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><thead><tr><td><strong>符號</strong></td><td><strong>說明</strong></td><td><strong>範例</strong></td></tr></thead><tbody><tr><td><strong>.</strong></td><td>匹配除了換行以外的任何單一字元</td><td><strong>a.c</strong> 可匹配 abc 或 a1c</td></tr><tr><td><strong>^</strong></td><td>匹配字串的開頭</td><td><strong>^Hello</strong> 必須以 Hello 開頭</td></tr><tr><td><strong>$</strong></td><td>匹配字串的結尾</td><td><strong>done$</strong> 必須以 done 結尾</td></tr><tr><td><strong>\</strong></td><td>轉義符號，用來搜尋原本就有特殊意義的符號</td><td><strong>\.</strong> 用來搜尋真正的點號</td></tr><tr><td><strong>[ ]</strong></td><td>匹配括號內的任一字元</td><td><strong>[aeiou]</strong> 匹配任何一個母音</td></tr><tr><td><strong>[^ ]</strong></td><td>不匹配括號內的任何字元</td><td><strong>[^0-9]</strong> 匹配任何非數字的字元</td></tr></tbody></table></figure>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">次數與位置的標記</h2>



<p>這些符號接在字元後面。用來指定前面的字元應該出現幾次。</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><thead><tr><td><strong>符號</strong></td><td><strong>說明</strong></td><td><strong>範例</strong></td></tr></thead><tbody><tr><td><strong>*</strong></td><td>出現 0 次或多次</td><td><strong>ab*</strong> 可匹配 a, ab, abb</td></tr><tr><td><strong>+</strong></td><td>出現 1 次或多次</td><td><strong>ab+</strong> 可匹配 ab, abb (不含 a)</td></tr><tr><td><strong>?</strong></td><td>出現 0 次或 1 次</td><td><strong>apples?</strong> 可匹配 apple 或 apples</td></tr><tr><td><strong>{n}</strong></td><td>剛好出現 n 次</td><td><strong>\d{3}</strong> 匹配 3 個數字</td></tr><tr><td><strong>{n,}</strong></td><td>出現至少 n 次</td><td><strong>\d{2,}</strong> 匹配 2 個以上的數字</td></tr><tr><td><strong>{n,m}</strong></td><td>出現 n 到 m 次</td><td><strong>\d{2,4}</strong> 匹配 2 到 4 個數字</td></tr></tbody></table></figure>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">常用字元群組</h2>



<p>為了方便縮寫，正則表達式提供了一些常用的預設符號。這能讓你的規則看起來更簡潔。</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><thead><tr><td><strong>符號</strong></td><td><strong>說明</strong></td><td><strong>同義表達式</strong></td></tr></thead><tbody><tr><td><strong>\d</strong></td><td>任何數字</td><td>[0-9]</td></tr><tr><td><strong>\D</strong></td><td>任何非數字</td><td>[^0-9]</td></tr><tr><td><strong>\w</strong></td><td>數字、英文字母或下底線</td><td>[a-zA-Z0-9_]</td></tr><tr><td><strong>\s</strong></td><td>任何空白字元 (空格、Tab、換行)</td><td>[ \f\n\r\t\v]</td></tr><tr><td><strong>\S</strong></td><td>任何非空白字元</td><td>[^ \f\n\r\t\v]</td></tr></tbody></table></figure>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">實戰應用範例1</h2>



<p>把上面的符號組合起來，就能處理生活中的各種需求。你可以參考下面的例子來練習。</p>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p>驗證手機號碼 (台灣格式)</p>



<p>^09\d{8}$</p>



<p>解釋：開頭必須是 09，後面接剛好 8 個數字。</p>
</blockquote>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p>簡單的電子郵件格式</p>



<p>\w+@\w+\.\w+</p>



<p>解釋：一串字元接 @，再接一串字元，最後接點號跟一段文字。</p>
</blockquote>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p>移除多餘的空白行</p>



<p>^\s*$</p>



<p>解釋：從開頭到結尾都只有空白或沒內容的行。</p>
</blockquote>



<p>正則表達式雖然看起來像外星語。但只要拆開來看，邏輯其實很固定。建議先從最基礎的符號開始試。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">實戰應用範例2</h2>



<p>你的需求是將 <code>com.app.a</code> 修改為 <code>com.app.b</code>。這裡有一個細節需要注意：你不希望誤改到像是 <code>com.lwfd.apple</code> 這種只是剛好開頭一樣的字串。因此，我們在寫正則表達式時，必須把「邊界」考慮進去。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">推薦的正則表達式語法</h2>



<p>你可以使用下面的規則來進行精確替換：</p>



<p>搜尋目標： com\.app\.a(?=[.;])|com\.app\.a\b</p>



<p>替換內容： com.app.b</p>



<p>這裡有幾個符號的作用說明：</p>



<ul class="wp-block-list">
<li><strong><code>\.</code></strong>：因為點號在正則中有特殊意義，所以要加反斜線，代表真正的「點」。</li>



<li><strong><code>(?=[.;])</code></strong>：這是一個前瞻斷言，表示後面必須接著分號或點號，但這部分不會被取代掉。</li>



<li><strong><code>\b</code></strong>：代表單字的邊界，確保 a 後面沒有接其他英文字母。</li>
</ul>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">實際操作指令</h2>



<p>使用我們之前討論的 Python 腳本，你可以直接在終端機輸入這行指令：</p>



<pre class="wp-block-code"><code>python replace_string.py ./src "com\.app\.a(?=&#91;.;])|com\.app\.a\b" "com.lwfd.b" "*.java"
</code></pre>



<p>這個指令會掃描 <code>src</code> 資料夾下所有的 Java 檔案。它會精確地把 <code>com.app.a;</code> 換成 <code>com.app.b;</code>，也會把 <code>com.app.a.abc</code> 換成 <code>com.app.b.abc</code>。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">為什麼這樣寫比較安全</h2>



<p>如果你只用 <code>com.app.a</code> 當關鍵字，萬一程式碼裡有 <code>com.app.archive</code>，它就會被錯誤地改成 <code>com.app.b rchive</code>，這會導致程式碼壞掉。加上邊界判斷（點號、分號或 <code>\b</code>）可以確保只改到你真正想要變動的部分。</p>



<p>這類替換通常發生在專案重構（Refactor）的時候。如果檔案數量很多，這行指令能幫你省下大約半小時的手動修改時間。</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>影像邊緣平滑與雜點清理</title>
		<link>https://codereview.max-everyday.com/smooth_sharp/</link>
		
		<dc:creator><![CDATA[max-code-review-usr1]]></dc:creator>
		<pubDate>Fri, 26 Dec 2025 16:43:30 +0000</pubDate>
				<category><![CDATA[Python]]></category>
		<category><![CDATA[字體]]></category>
		<category><![CDATA[image]]></category>
		<guid isPermaLink="false">https://codereview.max-everyday.com/?p=2059</guid>

					<description><![CDATA[處理影像遇到鋸齒。掃描圖檔常有雜點。這影響辨 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>處理影像遇到鋸齒。掃描圖檔常有雜點。這影響辨識準確。程式碼提供修復方案。利用骨架提取重建邊緣。搭配像素樣式比對清除雜訊。適合處理黑白文件或數位掃描圖。</p>



<p>Max腳本檔案下載：<br><a href="https://github.com/max32002/MaxFontScripts/blob/master/smooth_sharp.py">https://github.com/max32002/MaxFontScripts/blob/master/smooth_sharp.py</a></p>



<p>這個版本與「<a href="https://codereview.max-everyday.com/smooth_pattern/">套用多重濾鏡，精確修復各種特定的筆畫瑕疵</a>」這篇文章的差異在線條較圓滑，優點是產生的字型檔案會較小，缺點是，風格也消失的很嚴重，例如：預期的勾筆，會變成一個轉角的彎。</p>



<p>由於是使用scikit會造成交叉處可能被凸出或凹陷。這部份，等有空再來解，目前算是開發（除錯）中的版本。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">環境準備與安裝</h2>



<p>使用前需要準備開發環境。確保安裝 opencv-python 套件。還有 numpy 與 scikit-image。這些工具提供影像處理核心運算。</p>



<pre class="wp-block-code"><code>pip install opencv-python numpy scikit-image
</code></pre>



<h2 class="wp-block-heading">核心功能邏輯</h2>



<p>核心功能分為兩個階段。第一階段是 smooth_sharp_edges 函式。它提取影像骨架。計算每個點到邊緣的距離值。利用超取樣重新繪製平滑圓點。最後縮放回原始尺寸。這種做法能有效去除毛邊。</p>



<p>第二階段是 apply_pattern_cleaning_fast。這部分針對微小像素樣式進行清理。程式自動比對特定區塊。若符合定義的雜點特徵。就替換為正確像素。</p>



<h2 class="wp-block-heading">使用範例與指令</h2>



<p>程式支援單一檔案。也支援資料夾批次處理。透過命令列執行。參數 input 指定來源。參數 output 指定存放位置。</p>



<p>範例指令：</p>



<pre class="wp-block-code"><code>python smooth_sharp.py --input ./raw_images --output ./cleaned_results
</code></pre>



<p>如果沒有指定輸出路徑。程式會自動在輸入目錄旁建立新資料夾。處理完成的圖片會轉為白底黑字存檔。</p>



<h2 class="wp-block-heading">自定義清理樣式</h2>



<p>可以在 get_patterns 函式內擴充。定義 p 陣列為瑕疵樣式。定義 r 陣列為修正後的結果。程式會自動執行四個方向旋轉比對。不需要手動撰寫旋轉邏輯。這對處理特定硬體產生的掃描雜訊非常有效。</p>



<p>這是實用的影像預處理工具。適合處理黑白文字。或是改善手繪線條品質。</p>



<p></p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>套用多重濾鏡，精確修復各種特定的筆畫瑕疵</title>
		<link>https://codereview.max-everyday.com/smooth_pattern/</link>
		
		<dc:creator><![CDATA[max-code-review-usr1]]></dc:creator>
		<pubDate>Fri, 26 Dec 2025 13:44:46 +0000</pubDate>
				<category><![CDATA[字體]]></category>
		<category><![CDATA[Font]]></category>
		<category><![CDATA[image]]></category>
		<category><![CDATA[Python]]></category>
		<guid isPermaLink="false">https://codereview.max-everyday.com/?p=2048</guid>

					<description><![CDATA[為了方便擴展，我將程式結構重組。現在你可以定 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<figure class="wp-block-image size-full"><img fetchpriority="high" decoding="async" width="779" height="707" src="https://codereview.max-everyday.com/wp-content/uploads/2025/12/2025-12-26_07-55_k1.jpg?v=1766706943" alt="" class="wp-image-2049" srcset="https://codereview.max-everyday.com/wp-content/uploads/2025/12/2025-12-26_07-55_k1.jpg?v=1766706943 779w, https://codereview.max-everyday.com/wp-content/uploads/2025/12/2025-12-26_07-55_k1-230x209.jpg?v=1766706943 230w, https://codereview.max-everyday.com/wp-content/uploads/2025/12/2025-12-26_07-55_k1-350x318.jpg?v=1766706943 350w, https://codereview.max-everyday.com/wp-content/uploads/2025/12/2025-12-26_07-55_k1-480x436.jpg?v=1766706943 480w" sizes="(max-width: 779px) 100vw, 779px" /></figure>



<p>為了方便擴展，我將程式結構重組。現在你可以定義一個列表，裡面存放多組 <code>pattern</code> 與 <code>replacement</code> 的配對。程式會自動對每一組配對執行四個角度的旋轉掃描與替換。</p>



<p>Max腳本檔案下載：<br><a href="https://github.com/max32002/MaxFontScripts/blob/master/smooth_pattern.py">https://github.com/max32002/MaxFontScripts/blob/master/smooth_pattern.py</a></p>



<p>這個版本與「<a href="https://codereview.max-everyday.com/smooth_sharp/">影像邊緣平滑與雜點清理</a>」文章的差異在：優點是風格也消失較少，缺點：產生的字型檔案會較大，且雜訊較多。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">為什麼需要這份程式碼</h2>



<p>手寫筆記掃描成電腦檔案。墨水常常會暈開。筆畫黏在一起。畫面看起來很髒。這份程式碼可以自動修復。它能把黏住的字跡分開。清理多餘的碎點。讓黑白文字變得清晰。</p>



<h2 class="wp-block-heading">準備環境</h2>



<p>這段程式使用 Python 語言。你需要安裝兩個工具套件。打開終端機或命令提示字元。輸入下方指令安裝。</p>



<pre class="wp-block-code"><code>pip install opencv-python numpy</code></pre>



<h2 class="wp-block-heading">如何操作腳本</h2>



<p>你可以處理單張圖片。也可以處理整個資料夾。指令非常簡單。打開終端機。移動到檔案所在目錄。</p>



<p>處理單張圖片的範例。</p>



<pre class="wp-block-code"><code>python smooth_pattern.py -i test.jpg -o result.jpg
</code></pre>



<p>處理整個資料夾的範例。</p>



<pre class="wp-block-code"><code>python clean.py -i ./my_notes
</code></pre>



<p>如果沒有指定 output 路徑。程式會自動建立一個加上 &#8220;_clean&#8221; 字樣的資料夾。</p>



<h2 class="wp-block-heading">程式處理邏輯</h2>



<p>這份工具包含幾個重要步驟。首先將圖片轉為二值化。也就是純黑與純白。接著執行減少暈染。利用形態學運算切斷微小的連結。這對分離筆畫很有效。</p>



<p>程式定義了一些特定的像素樣式。會自動比對並替換雜訊。最後進行平滑化處理。先將圖片放大再縮小。利用中值濾波去除鋸齒。讓邊緣看起來更自然。</p>



<h2 class="wp-block-heading">建議</h2>



<p>對於學習 OpenCV 的初學者。這是一個很好的練習案例。可以觀察不同矩陣運算對圖片的影響。</p>



<p></p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>從unicode命名的圖片目錄裡刪除指定的檔案</title>
		<link>https://codereview.max-everyday.com/delete_by_char/</link>
		
		<dc:creator><![CDATA[max-code-review-usr1]]></dc:creator>
		<pubDate>Tue, 23 Dec 2025 05:03:30 +0000</pubDate>
				<category><![CDATA[Python]]></category>
		<guid isPermaLink="false">https://codereview.max-everyday.com/?p=2040</guid>

					<description><![CDATA[有時候我們會遇到一種特殊的檔案命名方式，例如 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>有時候我們會遇到一種特殊的檔案命名方式，例如檔案是用中文字的 Unicode 編碼命名的。手動刪除這些檔案既麻煩又容易出錯。</p>



<p>這篇文章要分享如何寫一個簡單的 Python 腳本，透過輸入中文字串或讀取文字檔，自動轉換編碼並刪除對應的檔案。</p>



<h3 class="wp-block-heading">核心邏輯介紹</h3>



<p>這支程式最關鍵的地方在於 <code>ord()</code> 函數。在 Python 中，這個函數可以把一個字元轉換成它對應的數字編碼。</p>



<p>例如：</p>



<ul class="wp-block-list">
<li><code>ord('佟')</code> 會得到 <code>20319</code></li>



<li><code>ord('佮')</code> 會得到 <code>20334</code></li>
</ul>



<p>我們只要結合這個邏輯與 <code>os</code> 模組，就能精準地刪除像 <code>20319.png</code> 這樣的檔案。</p>



<p>Max腳本檔案下載：<br><a href="https://github.com/max32002/MaxFontScripts/blob/master/delete_by_char.py">https://github.com/max32002/MaxFontScripts/blob/master/delete_by_char.py</a></p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">如何使用這個工具</h2>



<p>這支腳本提供了兩種靈活的使用方式，你可以根據情況選擇。</p>



<h3 class="wp-block-heading">1. 直接輸入字串</h3>



<p>如果你只想刪除少數幾個字對應的檔案，可以直接在終端機輸入：</p>



<pre class="wp-block-code"><code>python delete_by_char.py --string 佟佮</code></pre>



<p>程式會自動去抓 20319.png 和 20334.png 並將其刪除。</p>



<h3 class="wp-block-heading">2. 透過文字檔批次處理</h3>



<p>如果你有一大堆字要處理，可以先把這些字寫在一個 list.txt 檔案裡，然後執行：</p>



<pre class="wp-block-code"><code>python delete_by_char.py --file list.txt</code></pre>



<p>程式會讀取檔案內容，逐一轉換並清理檔案。</p>



<h3 class="wp-block-heading">3. 指定特定資料夾</h3>



<p>如果檔案不在當前目錄，可以加上 &#8211;path 參數：</p>



<pre class="wp-block-code"><code>python delete_by_char.py --path ./images --string 測試</code></pre>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">執行畫面</h2>



<figure class="wp-block-image size-full"><img decoding="async" width="479" height="582" src="https://codereview.max-everyday.com/wp-content/uploads/2025/12/2025-12-23_13-06_jt.jpg?v=1766466493" alt="" class="wp-image-2045" srcset="https://codereview.max-everyday.com/wp-content/uploads/2025/12/2025-12-23_13-06_jt.jpg?v=1766466493 479w, https://codereview.max-everyday.com/wp-content/uploads/2025/12/2025-12-23_13-06_jt-230x279.jpg?v=1766466493 230w, https://codereview.max-everyday.com/wp-content/uploads/2025/12/2025-12-23_13-06_jt-350x425.jpg?v=1766466493 350w" sizes="(max-width: 479px) 100vw, 479px" /></figure>



<p>這個人工去比對, 會眼花撩亂, 還會出錯, 用程式比對, 又快又有效率.</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">結語</h2>



<p>透過 Python 的 <code>argparse</code> 和 <code>ord</code> 函數，我們可以快速建立一個實用的工具。這種方法不但減少了人工對照檔名的時間，也降低了誤刪檔案的風險。記得在正式執行前，先確認你的路徑設定是否正確。</p>



<p></p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>字體檔匯出為SVG向量檔格式</title>
		<link>https://codereview.max-everyday.com/export_ttf_to_svg/</link>
		
		<dc:creator><![CDATA[max-code-review-usr1]]></dc:creator>
		<pubDate>Wed, 07 May 2025 04:56:35 +0000</pubDate>
				<category><![CDATA[Python]]></category>
		<category><![CDATA[字體]]></category>
		<guid isPermaLink="false">https://codereview.max-everyday.com/?p=1967</guid>

					<description><![CDATA[這個腳本會遍歷字型中的所有字元，並將每個 g [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>這個腳本會遍歷字型中的所有字元，並將每個 glyph 存成單獨的 .svg 檔案</p>



<h2 class="wp-block-heading">為什麼要學這個？</h2>



<p>在字型設計、視覺化應用、深度學習資料蒐集等領域中，我們常需要將 <code>.ttf</code> 字型檔案中的每個字元提取出來，轉換成標準向量格式（例如 <code>.svg</code>）。這種需求常見於以下情境：</p>



<ul class="wp-block-list">
<li>🎨 <strong>圖文設計師</strong>：將字型的特定字元轉為向量圖，供 Illustrator 或 Figma 編輯。</li>



<li>🧠 <strong>機器學習研究者</strong>：建立字型風格遷移、手寫模仿等模型時，需要大量向量化字元資料。</li>



<li>💻 <strong>前端工程師</strong>：將文字轉為 SVG，用於自訂字型圖示或動畫字效。</li>



<li>✍️ <strong>字型設計師</strong>：觀察並微調每個 glyph 的 SVG 輪廓。</li>
</ul>



<p>而手動一個一個轉出 SVG 不僅耗時，也容易出錯。幸好，透過 <code>FontForge</code> 提供的 Python API，我們可以輕鬆完成這個任務。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<p>前置作業</p>



<p>使用前，需要先安裝FontForge。</p>



<p>FontForge執行檔下載：<br><a href="https://fontforge.org/en-US/">https://fontforge.org/en-US/</a></p>



<p>Max腳本檔案下載：<br><a href="https://github.com/max32002/MaxFontScripts/blob/master/export_ttf_to_svg.py">https://github.com/max32002/MaxFontScripts/blob/master/export_ttf_to_svg.py</a></p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">使用範例</h2>



<p>假設你有一個叫做 <code>NotoSansCJKtc-Regular.ttf</code> 的中文字型檔，你可以執行以下指令：</p>



<pre class="wp-block-preformatted"><code>python export_ttf_to_svg.py ./fonts/NotoSansCJKtc-Regular.ttf ./output_svg<br></code></pre>



<p>執行後，程式會：</p>



<ul class="wp-block-list">
<li>開啟指定字型檔</li>



<li>將每個字元轉為 <code>.svg</code> 格式</li>



<li>儲存在 <code>./output_svg/</code> 資料夾中，命名為 glyph unicode int 值</li>
</ul>



<p>你可以在瀏覽器或設計工具中檢視這些 SVG，確認每個字元都完整向量化。</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">小結</h2>



<p>這個工具對於字型開發、字元資料集建立、視覺化工具客製化都有很大的幫助。透過簡單幾行 Python，你就可以自動化這個繁瑣的流程。</p>



<p>有一個特殊的情況, 需要手動地設定對應值到程式碼裡, 取得對應值是在下面這篇文章:<br><a href="https://codereview.max-everyday.com/get-font-chars/">https://codereview.max-everyday.com/get-font-chars/</a></p>



<p>之所以會有對應值, 是因為同一個字, 有多個異體字造成.</p>



<p>如果沒有產生正確的對應, 會造成某一個字碼會同時顯示二個字的 glyph.</p>



<hr class="wp-block-separator has-alpha-channel-opacity"/>



<h2 class="wp-block-heading">相關文章</h2>



<p>向量檔匯入字體檔<br><a href="https://codereview.max-everyday.com/import-svg-to-font/">https://codereview.max-everyday.com/import-svg-to-font/</a></p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>將您的圖片轉換為不同格式</title>
		<link>https://codereview.max-everyday.com/convert_images/</link>
		
		<dc:creator><![CDATA[max-code-review-usr1]]></dc:creator>
		<pubDate>Mon, 28 Apr 2025 16:51:58 +0000</pubDate>
				<category><![CDATA[Python]]></category>
		<guid isPermaLink="false">https://codereview.max-everyday.com/?p=1956</guid>

					<description><![CDATA[您是否厭倦了手動轉換大量圖片？透過這個進階的 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>您是否厭倦了手動轉換大量圖片？透過這個進階的 Python 腳本，您可以更方便地指定輸入和輸出目錄，並批量將圖片轉換為您想要的格式，預設為經典的黑白 <code>.pbm</code> 格式。</p>



<h2 class="wp-block-heading">為什麼要使用這個腳本？</h2>



<p>這個進階版本提供了更清晰和更方便的命令行參數：</p>



<ul class="wp-block-list">
<li><strong>更直觀的參數：</strong> 使用 <code>--input</code> 和 <code>--output</code> 參數來明確指定輸入和輸出目錄。</li>



<li><strong>強制指定目錄：</strong> 腳本會要求您提供輸入和輸出目錄，避免遺漏重要資訊。</li>



<li><strong>批量轉換：</strong> 仍然保留了高效批量轉換圖片的功能。</li>



<li><strong>靈活的格式：</strong> 支援轉換為 <code>.png</code>、<code>.jpg</code> 等多種常見圖片格式。</li>



<li><strong>組織輸出：</strong> 轉換後的檔案會自動保存到輸出目錄的子目錄中，方便管理。</li>
</ul>



<h2 class="wp-block-heading">使用方法</h2>



<p>請按照以下步驟使用這個進階腳本：</p>



<ol class="wp-block-list">
<li><strong>安裝 OpenCV 庫：</strong><br>如果尚未安裝，請打開您的終端機（macOS/Linux）或命令提示字元（Windows），然後輸入： <code>pip install opencv-python</code></li>



<li><strong>Max腳本檔案下載：</strong><br><a href="https://github.com/max32002/MaxFontScripts/blob/master/convert_images.py">https://github.com/max32002/MaxFontScripts/blob/master/<code>convert_images</code>.py</a></li>



<li><strong>開啟終端機或命令提示字元：</strong><br>導航到您儲存 <code>convert_images.py</code> 檔案的目錄。</li>



<li><strong>執行腳本：</strong><br>使用 <code>--input</code> 和 <code>--output</code> 參數指定輸入和輸出目錄，並可選地使用 <code>-f</code> 或 <code>--format</code> 參數指定輸出格式。</li>
</ol>



<h2 class="wp-block-heading">基本使用範例<br></h2>



<p><strong>範例 1：將 input_images 目錄中的所有圖片轉換為預設的 .pbm 格式，並保存到 converted_images 目錄下的 pbm_converted 子目錄中。</strong></p>



<pre class="wp-block-code"><code>python convert_images.py --input input_images --output converted_images</code></pre>



<p><strong>範例 2：將 source_photos 目錄中的所有圖片轉換為 .png 格式，並保存到 output_photos 目錄下的 png_converted 子目錄中。</strong></p>



<pre class="wp-block-code"><code>python convert_images.py --input source_photos --output output_photos -f png</code></pre>



<p><strong>範例 3：將 <code>images_to_process</code> 目錄中的所有圖片轉換為 <code>.jpg</code> 格式，並保存到 <code>processed_images</code> 目錄下的 <code>jpg_converted</code> 子目錄中。</strong> </p>



<pre class="wp-block-code"><code>python convert_images.py --input images_to_process --output processed_images --format jpg</code></pre>



<h2 class="wp-block-heading">進階使用範例</h2>



<p>假設你的輸入目錄是 <code>input_imgs</code>，輸出目錄是 <code>output_imgs</code>。</p>



<p><strong>1. 基本轉換 (無 Resize):</strong></p>



<pre class="wp-block-code"><code>python convert_images.py --input input_imgs --output output_imgs -f jpg
</code></pre>



<p><em>你會看到一個漂亮的進度條在跑。</em></p>



<p><strong>2. 強制 Resize 到指定寬高 (例如 800&#215;600):</strong></p>



<pre class="wp-block-code"><code>python convert_images.py --input input_imgs --output output_imgs -f png --width 800 --height 600
</code></pre>



<p><strong>3. 指定寬度，高度自動按比例縮放 (例如寬度固定為 1024):</strong></p>



<pre class="wp-block-code"><code>python convert_images.py --input input_imgs --output output_imgs -f jpg --width 1024
</code></pre>



<p><strong>4. 指定高度，寬度自動按比例縮放 (例如高度固定為 500):</strong></p>



<pre class="wp-block-code"><code>python convert_images.py --input input_imgs --output output_imgs -f jpg --height 500</code></pre>



<p></p>
]]></content:encoded>
					
		
		
			</item>
	</channel>
</rss>
