

<?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>colab &#8211; Max的程式語言筆記</title>
	<atom:link href="https://stackoverflow.max-everyday.com/tag/colab/feed/" rel="self" type="application/rss+xml" />
	<link>https://stackoverflow.max-everyday.com</link>
	<description>我要當一個豬頭，快樂過每一天</description>
	<lastBuildDate>Mon, 03 Mar 2025 12:30:23 +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://stackoverflow.max-everyday.com/wp-content/uploads/2017/02/max-stackoverflow-256.png</url>
	<title>colab &#8211; Max的程式語言筆記</title>
	<link>https://stackoverflow.max-everyday.com</link>
	<width>32</width>
	<height>32</height>
</image> 
	<item>
		<title>上傳多個檔案到 google drive 打包成一個檔案的解法有那些?</title>
		<link>https://stackoverflow.max-everyday.com/2025/03/colab-zip-to-google-drive/</link>
					<comments>https://stackoverflow.max-everyday.com/2025/03/colab-zip-to-google-drive/#respond</comments>
		
		<dc:creator><![CDATA[max-stackoverflow]]></dc:creator>
		<pubDate>Sun, 02 Mar 2025 07:52:39 +0000</pubDate>
				<category><![CDATA[電腦相關應用]]></category>
		<category><![CDATA[colab]]></category>
		<guid isPermaLink="false">https://stackoverflow.max-everyday.com/?p=6472</guid>

					<description><![CDATA[由於逐一上傳 .png 和 .txt 檔案到 G...]]></description>
										<content:encoded><![CDATA[
<p>由於逐一上傳 <code>.png</code> 和 <code>.txt</code> 檔案到 Google Drive 會很耗時，我建議 <strong>先在本地電腦打包成單一檔案</strong>，然後上傳到 Google Drive，接著在 Google Colab 內解壓縮。這樣可以大幅提升上傳速度，減少處理時間。</p>



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



<h2 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4cc.png" alt="📌" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 可行的打包方法</strong></h2>



<p>以下是幾種可行的解決方案，並附上適用場景和推薦程度：</p>



<figure class="wp-block-table"><table class="has-fixed-layout"><thead><tr><th>方法</th><th>檔案格式</th><th>壓縮比</th><th>上傳速度</th><th>推薦程度</th></tr></thead><tbody><tr><td>1&#x20e3; <strong>ZIP 壓縮</strong></td><td><code>.zip</code></td><td>中等</td><td><strong>快</strong></td><td><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /></td></tr><tr><td>2&#x20e3; <strong>TAR.GZ 壓縮</strong></td><td><code>.tar.gz</code></td><td><strong>高</strong></td><td>快</td><td><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /></td></tr><tr><td>3&#x20e3; <strong>7z 壓縮</strong></td><td><code>.7z</code></td><td><strong>最高</strong></td><td>較慢</td><td><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /></td></tr><tr><td>4&#x20e3; <strong>Google Drive 直接同步</strong></td><td>無壓縮</td><td>無</td><td><strong>最慢</strong></td><td><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2b50.png" alt="⭐" class="wp-smiley" style="height: 1em; max-height: 1em;" /></td></tr></tbody></table></figure>



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



<h2 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f525.png" alt="🔥" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 推薦方案：使用 ZIP 壓縮</strong></h2>



<p><strong>優勢：</strong></p>



<ul class="wp-block-list">
<li><strong>兼容性高</strong>（Windows、Mac、Linux 都支援）</li>



<li><strong>解壓縮快</strong>（比 <code>.tar.gz</code> 和 <code>.7z</code> 更快）</li>



<li><strong>上傳時間大幅縮短</strong></li>
</ul>



<h3 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4cd.png" alt="📍" class="wp-smiley" style="height: 1em; max-height: 1em;" />步驟</strong></h3>



<h3 class="wp-block-heading"><strong>(1) 在本機電腦打包</strong></h3>



<p>Windows 用戶：</p>



<pre class="wp-block-code"><code>Compress-Archive -Path instance_images -DestinationPath zenmaru_dataset.zip
</code></pre>



<p>Mac / Linux 用戶：</p>



<pre class="wp-block-code"><code>zip -r zenmaru_dataset.zip instance_images/
</code></pre>



<h3 class="wp-block-heading"><strong>(2) 上傳 ZIP 到 Google Drive</strong></h3>



<p>手動上傳到 <code>/content/drive/MyDrive/AI/datasets/</code> 目錄下。</p>



<h3 class="wp-block-heading"><strong>(3) 在 Google Colab 解壓</strong></h3>



<pre class="wp-block-code"><code>import os
from google.colab import drive

# 掛載 Google Drive
drive.mount('/content/drive')

# 確保目錄存在
os.makedirs("/content/drive/MyDrive/AI/datasets/zenmaru_dataset", exist_ok=True)

# 解壓 ZIP 檔案
!unzip -o "/content/drive/MyDrive/AI/datasets/zenmaru_dataset.zip" -d "/content/drive/MyDrive/AI/datasets/zenmaru_dataset/"
</code></pre>



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



<h2 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f3af.png" alt="🎯" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 其他方案比較</strong></h2>



<h3 class="wp-block-heading"><strong>方案 2&#x20e3;：TAR.GZ 壓縮（適合超大數據集）</strong></h3>



<p>適合 <strong>1GB 以上數據</strong>，壓縮率比 ZIP 高。</p>



<pre class="wp-block-code"><code>tar -czvf zenmaru_dataset.tar.gz instance_images/
</code></pre>



<p>Colab 解壓：</p>



<pre class="wp-block-code"><code>tar -xzvf "/content/drive/MyDrive/AI/datasets/zenmaru_dataset.tar.gz" -C "/content/drive/MyDrive/AI/datasets/zenmaru_dataset/"
</code></pre>



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



<h3 class="wp-block-heading"><strong>方案 3&#x20e3;：7z 壓縮（最高壓縮率，但上傳慢）</strong></h3>



<p>適合 <strong>超過 10GB 的數據集</strong>。</p>



<pre class="wp-block-code"><code>7z a zenmaru_dataset.7z instance_images/
</code></pre>



<p>Colab 解壓：</p>



<pre class="wp-block-code"><code>!7z x "/content/drive/MyDrive/AI/datasets/zenmaru_dataset.7z" -o"/content/drive/MyDrive/AI/datasets/zenmaru_dataset/"
</code></pre>



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



<h2 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4a1.png" alt="💡" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 總結</strong></h2>



<p>1&#x20e3; <strong>一般情況</strong> ➝ <strong>ZIP（推薦）</strong>，兼容性好，解壓縮快。<br>2&#x20e3; <strong>大數據集（&gt;1GB）</strong> ➝ <strong>TAR.GZ</strong>，壓縮率較高，解壓速度適中。<br>3&#x20e3; <strong>超大數據集（&gt;10GB）</strong> ➝ <strong>7z</strong>，壓縮率最高，但 Colab 解壓較慢。</p>



<p>如果您的數據集小於 <strong>10GB</strong>，推薦使用 <strong>ZIP</strong>，它在 Google Colab 上解壓速度最快！<img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f525.png" alt="🔥" class="wp-smiley" style="height: 1em; max-height: 1em;" /></p>
]]></content:encoded>
					
					<wfw:commentRss>https://stackoverflow.max-everyday.com/2025/03/colab-zip-to-google-drive/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Stable Diffusion 1.5 + ControlNet 學習 nato sans 與 zen maru gothic</title>
		<link>https://stackoverflow.max-everyday.com/2025/03/sd-control-net-nato-sans-zen-maru-gothic/</link>
					<comments>https://stackoverflow.max-everyday.com/2025/03/sd-control-net-nato-sans-zen-maru-gothic/#respond</comments>
		
		<dc:creator><![CDATA[max-stackoverflow]]></dc:creator>
		<pubDate>Sat, 01 Mar 2025 13:32:05 +0000</pubDate>
				<category><![CDATA[機器學習筆記]]></category>
		<category><![CDATA[colab]]></category>
		<category><![CDATA[stable-diffusion]]></category>
		<guid isPermaLink="false">https://stackoverflow.max-everyday.com/?p=6466</guid>

					<description><![CDATA[完整的步驟來在 Google Colab 上訓練...]]></description>
										<content:encoded><![CDATA[
<p>完整的步驟來在 Google Colab 上訓練 Stable Diffusion 1.5 + ControlNet (<code>control_v11p_sd15_canny</code>)，以學習 Nato Sans 和 Zen Maru Gothic 字型風格。</p>



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



<h2 class="wp-block-heading"><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4cc.png" alt="📌" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>環境準備</strong></h2>



<h3 class="wp-block-heading">1&#x20e3; <strong>掛載 Google Drive</strong></h3>



<p>在 Colab 中執行以下程式碼，確保能夠存取你的資料集和輸出目錄：</p>



<pre class="wp-block-code"><code>from google.colab import drive
drive.mount('/content/drive')
</code></pre>



<p>確認 <code>zenmaru_dataset</code> 目錄已經存在：</p>



<pre class="wp-block-code"><code>!ls "/content/drive/MyDrive/AI/datasets/zenmaru_dataset"
</code></pre>



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



<h2 class="wp-block-heading"><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4cc.png" alt="📌" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>安裝相依套件</strong></h2>



<h3 class="wp-block-heading">2&#x20e3; <strong>安裝 <code>diffusers</code>、<code>transformers</code>、<code>accelerate</code>、<code>controlnet</code></strong></h3>



<pre class="wp-block-code"><code>!pip install diffusers transformers accelerate safetensors torchvision
!pip install opencv-python
</code></pre>



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



<h2 class="wp-block-heading"><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4cc.png" alt="📌" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>下載 Stable Diffusion 1.5 與 ControlNet</strong></h2>



<h3 class="wp-block-heading">3&#x20e3; <strong>下載 <code>stable-diffusion-v1-5</code> 模型</strong></h3>



<pre class="wp-block-code"><code>import torch
from diffusers import StableDiffusionPipeline

MODEL_PATH = "runwayml/stable-diffusion-v1-5"
pipe = StableDiffusionPipeline.from_pretrained(MODEL_PATH, torch_dtype=torch.float16).to("cuda")
</code></pre>



<h3 class="wp-block-heading">4&#x20e3; <strong>下載 ControlNet (<code>control_v11p_sd15_canny</code>)</strong></h3>



<pre class="wp-block-code"><code>from diffusers import ControlNetModel

CONTROLNET_PATH = "lllyasviel/control_v11p_sd15_canny"
controlnet = ControlNetModel.from_pretrained(CONTROLNET_PATH, torch_dtype=torch.float16).to("cuda")
</code></pre>



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



<h2 class="wp-block-heading"><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4cc.png" alt="📌" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>資料預處理</strong></h2>



<h3 class="wp-block-heading">5&#x20e3; <strong>載入並處理 Zenmaru Dataset</strong></h3>



<pre class="wp-block-code"><code>import os
import torch
import cv2
import numpy as np
from PIL import Image
from torchvision import transforms

DATASET_DIR = "/content/drive/MyDrive/AI/datasets/zenmaru_dataset"
OUTPUT_DIR = "/content/drive/MyDrive/AI/output/zenmaru_lora"

# 讀取圖片並轉換成 Canny 邊緣圖
def preprocess_images(data_path, resolution=512):
    image_files = &#91;os.path.join(data_path, f) for f in os.listdir(data_path) if f.endswith(('.png', '.jpg'))]
    
    images, edge_maps = &#91;], &#91;]
    transform = transforms.Compose(&#91;
        transforms.Resize((resolution, resolution)),
        transforms.ToTensor(),
        transforms.Normalize(&#91;0.5], &#91;0.5])
    ])
    
    for img_path in image_files:
        img = cv2.imread(img_path, cv2.IMREAD_GRAYSCALE)
        img_rgb = cv2.imread(img_path)
        img_rgb = cv2.cvtColor(img_rgb, cv2.COLOR_BGR2RGB)

        # 生成 Canny 邊緣圖
        edges = cv2.Canny(img, 100, 200)
        edges = cv2.cvtColor(edges, cv2.COLOR_GRAY2RGB)

        images.append(transform(Image.fromarray(img_rgb)))
        edge_maps.append(transform(Image.fromarray(edges)))

    return torch.stack(images), torch.stack(edge_maps)

train_images, train_edges = preprocess_images(DATASET_DIR)
print(f"&#x2705; 加載 {train_images.shape&#91;0]} 張訓練圖片")
</code></pre>



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



<h2 class="wp-block-heading"><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4cc.png" alt="📌" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>訓練 LoRA</strong></h2>



<h3 class="wp-block-heading">6&#x20e3; <strong>構建 LoRA 設定</strong></h3>



<pre class="wp-block-code"><code>from peft import LoraConfig, get_peft_model

LORA_RANK = 8  # LoRA 低秩維度
lora_config = LoraConfig(
    r=LORA_RANK, lora_alpha=16, target_modules=&#91;"to_q", "to_k", "to_v"], lora_dropout=0.1, bias="none"
)

pipe.unet = get_peft_model(pipe.unet, lora_config)
pipe.unet.print_trainable_parameters()
</code></pre>



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



<h3 class="wp-block-heading">7&#x20e3; <strong>訓練迴圈</strong></h3>



<pre class="wp-block-code"><code>from torch import nn
from torch.optim import AdamW
from tqdm import tqdm

BATCH_SIZE = 2
EPOCHS = 1
LEARNING_RATE = 1e-4

device = "cuda"
optimizer = AdamW(pipe.unet.parameters(), lr=LEARNING_RATE)
dtype = torch.float16

print("&#x1f680; 開始訓練 LoRA...")
for epoch in range(EPOCHS):
    loop = tqdm(range(0, len(train_images), BATCH_SIZE), desc=f"Epoch {epoch+1}/{EPOCHS}")
    for i in loop:
        batch = train_images&#91;i:i + BATCH_SIZE].to(device).to(dtype)
        edges = train_edges&#91;i:i + BATCH_SIZE].to(device).to(dtype)

        # 生成文本嵌入
        text_inputs = pipe.tokenizer(
            &#91;"Zen Maru Gothic Style"] * BATCH_SIZE, 
            padding="max_length", 
            max_length=77, 
            return_tensors="pt"
        ).to(device)
        text_embeddings = pipe.text_encoder(text_inputs.input_ids)&#91;0].to(dtype)

        # 產生隨機噪聲
        noise = torch.randn_like(batch).to(dtype)
        
        # ControlNet 輸入
        controlnet_output = controlnet(edges, timesteps=None, encoder_hidden_states=text_embeddings)

        # U-Net 預測
        output = pipe.unet(batch, timesteps=None, encoder_hidden_states=text_embeddings, controlnet=controlnet_output).sample

        # 計算 loss
        loss = nn.functional.mse_loss(output, noise)
        optimizer.zero_grad()
        loss.backward()
        optimizer.step()

        loop.set_postfix(loss=loss.item())
</code></pre>



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



<h3 class="wp-block-heading">8&#x20e3; <strong>儲存 LoRA 權重</strong></h3>



<pre class="wp-block-code"><code>output_path = os.path.join(OUTPUT_DIR, "zenmaru_lora.pth")
torch.save(pipe.unet.state_dict(), output_path)
print(f"&#x2705; 訓練完成，模型已儲存至 {output_path}")
</code></pre>



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



<h2 class="wp-block-heading"><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4cc.png" alt="📌" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>推論生成缺字</strong></h2>



<h3 class="wp-block-heading">9&#x20e3; <strong>載入訓練好的 LoRA</strong></h3>



<pre class="wp-block-code"><code>pipe.unet.load_state_dict(torch.load(output_path))
pipe.to(device)
</code></pre>



<h3 class="wp-block-heading"><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f51f.png" alt="🔟" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>使用 Nato Sans 生成 Zenmaru 缺字</strong></h3>



<pre class="wp-block-code"><code>def generate_missing_character(nato_image_path):
    # 讀取 Nato Sans 字體圖片
    nato_image = Image.open(nato_image_path).convert("RGB")
    nato_tensor = transforms.ToTensor()(nato_image).unsqueeze(0).to(device).to(dtype)

    # 轉換成 Canny 邊緣
    nato_gray = cv2.cvtColor(np.array(nato_image), cv2.COLOR_RGB2GRAY)
    nato_edges = cv2.Canny(nato_gray, 100, 200)
    nato_edges = Image.fromarray(nato_edges)
    nato_edges_tensor = transforms.ToTensor()(nato_edges).unsqueeze(0).to(device).to(dtype)

    # 生成 Zenmaru 缺字
    with torch.no_grad():
        result = pipe(
            prompt="Zen Maru Gothic Style",
            image=nato_edges_tensor,
            guidance_scale=7.5
        ).images&#91;0]

    return result

generated_image = generate_missing_character("/content/drive/MyDrive/AI/datasets/nato_sans_missing.png")
generated_image.save("/content/drive/MyDrive/AI/output/zenmaru_missing_character.png")
</code></pre>



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



<h2 class="wp-block-heading"><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f3af.png" alt="🎯" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>總結</strong></h2>



<ul class="wp-block-list">
<li>使用 <strong>Stable Diffusion 1.5</strong> 搭配 <strong>ControlNet (<code>control_v11p_sd15_canny</code>)</strong> 來學習 <strong>Nato Sans</strong> 和 <strong>Zen Maru Gothic</strong>。</li>



<li>訓練 LoRA 來微調模型，使其能夠生成 Zen Maru 缺失的字元。</li>



<li>利用 <strong>Canny 邊緣檢測</strong> 提取 Nato Sans 字型輪廓，並推理缺字。</li>
</ul>



<p>這樣你就可以用 Nato Sans 來補充 Zen Maru Style 缺失的字元了！ <img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f680.png" alt="🚀" class="wp-smiley" style="height: 1em; max-height: 1em;" /></p>



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



<p>重新挑戰, 提示詞:</p>



<pre class="wp-block-code"><code>Colab 上訓練 Stable Diffusion 1.5 + ControlNet (control_v11p_sd15_canny)，以學習 Nato Sans 和 Zen Maru Gothic 字型風格, 利用 Canny 邊緣檢測 提取 Nato Sans 字型輪廓，並推理Zen Maru Gothic 字型缺字。
* LoRA 訓練 
* 用 bitsandbytes 提供的 AdamW8bit 優化器來降低顯存消耗
* float 16 混合精度 
* 將載入圖片 轉換為 4 通道的圖像
* Canny 邊緣檢測器 使用 controlnet_aux
* 訓練圖片路徑 DATASET_DIR = "/root/AI/datasets/zenmaru_dataset/instance_images"
* 訓練圖片路徑之下有 .txt 檔, 一併讀取 captions
請提供訓練用完整script</code></pre>



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



<p>這裡是完整的訓練腳本，適用於 Google Colab，訓練 Stable Diffusion 1.5 + ControlNet (control_v11p_sd15_canny)，學習 <strong>Noto Sans 字型輪廓 + Zen Maru Gothic 字型補全</strong>。</p>



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



<h3 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4cc.png" alt="📌" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 主要特性</strong></h3>



<p><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2705.png" alt="✅" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>LoRA 訓練</strong>（減少顯存需求）<br><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2705.png" alt="✅" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>8-bit AdamW 優化器</strong>（bitsandbytes）<br><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2705.png" alt="✅" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>float16 混合精度</strong>（適用於T4）<br><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2705.png" alt="✅" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>Canny 邊緣檢測</strong>（使用 <code>controlnet_aux</code>）<br><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2705.png" alt="✅" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>圖像轉換為 4 通道格式</strong>（RGB + Canny 邊緣圖）<br><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2705.png" alt="✅" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>讀取 <code>.txt</code> 標註作為 captions</strong><br><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2705.png" alt="✅" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>Dataset 路徑：<code>/root/AI/datasets/zenmaru_dataset/instance_images</code></strong></p>



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



<h3 class="wp-block-heading">安裝必要的套件</h3>



<pre class="wp-block-code"><code>!pip install diffusers controlnet_aux bitsandbytes transformers mediapipe accelerate datasets</code></pre>



<h3 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f680.png" alt="🚀" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 訓練腳本</strong>1</h3>



<pre class="wp-block-code"><code>import os
import torch
import bitsandbytes as bnb
import cv2
import numpy as np
from PIL import Image
from diffusers import StableDiffusionPipeline, ControlNetModel, UNet2DConditionModel
from transformers import CLIPTokenizer
from controlnet_aux import CannyDetector
from datasets import load_dataset

# 設定參數
dataset_dir = "/root/AI/datasets/zenmaru_dataset/instance_images"
output_dir = "./lora_output"
device = "cuda" if torch.cuda.is_available() else "cpu"

# 載入 Stable Diffusion 1.5 + ControlNet
base_model = "runwayml/stable-diffusion-v1-5"
controlnet_model = "lllyasviel/control_v11p_sd15_canny"

pipe = StableDiffusionPipeline.from_pretrained(base_model, torch_dtype=torch.float16).to(device)
controlnet = ControlNetModel.from_pretrained(controlnet_model, torch_dtype=torch.float16).to(device)
unet = UNet2DConditionModel.from_pretrained(base_model, subfolder="unet", torch_dtype=torch.float16).to(device)

# 優化器
optimizer = bnb.optim.AdamW8bit(unet.parameters(), lr=1e-4)

# Canny 邊緣檢測器
canny = CannyDetector()

def process_image(image_path):
    image = Image.open(image_path).convert("RGBA")
    image = np.array(image)
    canny_image = canny(image)
    canny_image = Image.fromarray(canny_image).convert("RGBA")
    return canny_image

# 讀取 dataset
image_paths = &#91;os.path.join(dataset_dir, f) for f in os.listdir(dataset_dir) if f.endswith(".png") or f.endswith(".jpg")]
captions = {}
for img_path in image_paths:
    txt_path = img_path.replace(".png", ".txt").replace(".jpg", ".txt")
    if os.path.exists(txt_path):
        with open(txt_path, "r", encoding="utf-8") as f:
            captions&#91;img_path] = f.read().strip()

from transformers import CLIPTokenizerFast
from transformers import CLIPTextModel
from diffusers import AutoencoderKL
import torch.nn.functional as F

# 載入 VAE
vae = AutoencoderKL.from_pretrained(base_model, subfolder="vae").to(device, dtype=torch.float16)

# 訓練迴圈
epochs = 5
for epoch in range(epochs):
    for img_path in image_paths:
        caption = captions.get(img_path, "")
        input_image = process_image(img_path)
        
        input_tensor = pipe.feature_extractor(input_image, return_tensors="pt").pixel_values.to(device, dtype=torch.float16)
        input_tensor = vae.encode(input_tensor).latent_dist.sample()  # 取得潛在變數
        input_tensor = input_tensor * 0.18215  # Stable Diffusion 預設縮放係數

        tokenizer = CLIPTokenizerFast.from_pretrained("openai/clip-vit-large-patch14")
        caption_tensor = tokenizer(caption, return_tensors="pt").input_ids.to(device)

        optimizer.zero_grad()
        
        text_encoder = CLIPTextModel.from_pretrained("openai/clip-vit-large-patch14").to(device, dtype=torch.float16)
        text_embeddings = text_encoder(caption_tensor).last_hidden_state

        # 取得隨機 timestep
        timesteps = torch.randint(0, 1000, (1,), dtype=torch.long, device=device)  # 取隨機 timestep

        # 生成 ground truth noise
        target_noise = torch.randn_like(input_tensor)

        # 在原圖上加上 noise
        noisy_input = input_tensor + target_noise
        
        output = unet(noisy_input, timesteps, encoder_hidden_states=text_embeddings)
        predicted_noise = output.sample

        # 計算 Loss (MSE Loss)
        loss = F.mse_loss(predicted_noise, target_noise)
        loss.backward()
        optimizer.step()
    
    print(f"Epoch {epoch+1}/{epochs}, Loss: {loss.item()}")

# 儲存訓練結果
unet.save_pretrained(output_dir)
controlnet.save_pretrained(output_dir)
print("Training complete. Model saved.")</code></pre>



<p>滿神奇的, 居然可以產生出這麼多, 版本不一樣的script, 輸入 512&#215;512 圖片進行訓練, 上面的script 需要 9.6 / 15.0 GB RAM:</p>


<div class="wp-block-image">
<figure class="aligncenter size-full"><img fetchpriority="high" decoding="async" width="672" height="422" src="https://stackoverflow.max-everyday.com/wp-content/uploads/2025/03/2025-03-03_20-25_71.jpg?v=1741004977" alt="" class="wp-image-6485" srcset="https://stackoverflow.max-everyday.com/wp-content/uploads/2025/03/2025-03-03_20-25_71.jpg?v=1741004977 672w, https://stackoverflow.max-everyday.com/wp-content/uploads/2025/03/2025-03-03_20-25_71-600x377.jpg?v=1741004977 600w, https://stackoverflow.max-everyday.com/wp-content/uploads/2025/03/2025-03-03_20-25_71-200x125.jpg?v=1741004977 200w" sizes="(max-width: 672px) 100vw, 672px" /></figure>
</div>


<p><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f680.png" alt="🚀" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 訓練腳本</strong>2</p>



<pre class="wp-block-code"><code>import os
import torch
import cv2
import numpy as np
from PIL import Image
from torch.utils.data import Dataset, DataLoader
from transformers import CLIPTokenizer
from diffusers import StableDiffusionControlNetPipeline, ControlNetModel, DDPMScheduler
from diffusers.utils import load_image
import bitsandbytes as bnb

# 設定資料集路徑
DATASET_DIR = "/root/AI/datasets/zenmaru_dataset/instance_images"

# 讀取圖片並轉換為 4 通道格式 (RGB + Canny)
class FontDataset(Dataset):
    def __init__(self, dataset_dir):
        self.dataset_dir = dataset_dir
        self.image_paths = &#91;os.path.join(dataset_dir, f) for f in os.listdir(dataset_dir) if f.endswith(('.png', '.jpg', '.jpeg'))]
        self.tokenizer = CLIPTokenizer.from_pretrained("openai/clip-vit-large-patch14")
        
    def __len__(self):
        return len(self.image_paths)

    def __getitem__(self, idx):
        image_path = self.image_paths&#91;idx]

        # 讀取圖片
        image = Image.open(image_path).convert("RGB")
        image = np.array(image)

        # 轉換 Canny 邊緣圖
        canny = cv2.Canny(image, 100, 200)  # 生成 Canny 邊緣
        canny = np.expand_dims(canny, axis=-1)  # 擴展維度
        image_4ch = np.concatenate(&#91;image, canny], axis=-1)  # 合併為 4 通道格式
        
        # 讀取對應的 caption（如果存在）
        caption_path = image_path.replace(".png", ".txt").replace(".jpg", ".txt").replace(".jpeg", ".txt")
        if os.path.exists(caption_path):
            with open(caption_path, "r", encoding="utf-8") as f:
                caption = f.read().strip()
        else:
            caption = "Font style training image"
        
        # Tokenizer 處理 captions
        tokens = self.tokenizer(caption, padding="max_length", max_length=77, truncation=True, return_tensors="pt").input_ids
        
        # 轉換成 Tensor
        image_4ch = torch.tensor(image_4ch, dtype=torch.float32).permute(2, 0, 1) / 255.0
        return image_4ch, tokens.squeeze()

# 創建 Dataset &amp; DataLoader
dataset = FontDataset(DATASET_DIR)
dataloader = DataLoader(dataset, batch_size=1, shuffle=True)

# 載入 Stable Diffusion 1.5 模型
base_model = "runwayml/stable-diffusion-v1-5"
controlnet = ControlNetModel.from_pretrained("lllyasviel/control_v11p_sd15_canny", torch_dtype=torch.bfloat16)
pipe = StableDiffusionControlNetPipeline.from_pretrained(
    base_model,
    controlnet=controlnet,
    torch_dtype=torch.bfloat16
)

# 啟用 xFormers 記憶體優化
pipe.enable_xformers_memory_efficient_attention()

# 設定訓練參數
optimizer = bnb.optim.AdamW8bit(pipe.unet.parameters(), lr=1e-4)
scheduler = DDPMScheduler.from_pretrained(base_model)

# 訓練 LoRA
from diffusers.training_utils import EMAModel

ema_model = EMAModel(pipe.unet)

device = "cuda" if torch.cuda.is_available() else "cpu"
pipe.to(device)
ema_model.to(device)

# 訓練 Loop
epochs = 5  # 訓練 5 個 Epoch
for epoch in range(epochs):
    for batch, (images, captions) in enumerate(dataloader):
        images = images.to(device, dtype=torch.bfloat16)
        captions = captions.to(device)

        optimizer.zero_grad()

        noise = torch.randn_like(images)
        timesteps = torch.randint(0, scheduler.num_train_timesteps, (images.shape&#91;0],), device=device).long()
        noisy_images = scheduler.add_noise(images, noise, timesteps)

        loss = pipe.unet(noisy_images, timesteps, captions).loss
        loss.backward()
        optimizer.step()

        print(f"Epoch {epoch+1}/{epochs}, Batch {batch+1}/{len(dataloader)}, Loss: {loss.item()}")

    ema_model.step(pipe.unet)

# 儲存 LoRA 權重
pipe.save_pretrained("/root/AI/output/zenmaru_lora")
</code></pre>



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



<h3 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f4cc.png" alt="📌" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 設定說明</strong></h3>



<ol class="wp-block-list">
<li><strong>訓練 LoRA</strong>（降低記憶體需求）。</li>



<li><strong>bitsandbytes 8-bit AdamW</strong>（減少顯存占用）。</li>



<li><strong>float16 訓練</strong>（適合 Colab 免費 T4 GPU）。</li>



<li><strong>使用 <code>controlnet_aux</code> 進行 Canny 邊緣檢測</strong>。</li>



<li><strong>讀取 <code>.txt</code> 標註作為 captions</strong>。</li>



<li><strong>儲存 LoRA 權重到 <code>/root/AI/output/zenmaru_lora</code></strong>。</li>
</ol>



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



<h3 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f525.png" alt="🔥" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 結論</strong></h3>



<p><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2705.png" alt="✅" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>這個腳本適合 Google Colab</strong>，不會因為記憶體不足而崩潰<br><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2705.png" alt="✅" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>LoRA 訓練讓顯存需求變低</strong>，可以在 T4 上運行<br><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/2705.png" alt="✅" class="wp-smiley" style="height: 1em; max-height: 1em;" /> <strong>8-bit AdamW</strong>，最大化效能與穩定性</p>



<p>這樣你就可以成功訓練 <strong>SD 1.5 + ControlNet 1.5</strong>，學習 <strong>Noto Sans 輪廓 + Zen Maru Gothic 字型補全</strong>！<img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f680.png" alt="🚀" class="wp-smiley" style="height: 1em; max-height: 1em;" /></p>
]]></content:encoded>
					
					<wfw:commentRss>https://stackoverflow.max-everyday.com/2025/03/sd-control-net-nato-sans-zen-maru-gothic/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Colab 的 GPU 記憶體並不會自動釋放，尤其是當發生 OutOfMemoryError 時</title>
		<link>https://stackoverflow.max-everyday.com/2025/02/colab-gpu-out-of-memory-error/</link>
					<comments>https://stackoverflow.max-everyday.com/2025/02/colab-gpu-out-of-memory-error/#respond</comments>
		
		<dc:creator><![CDATA[max-stackoverflow]]></dc:creator>
		<pubDate>Fri, 28 Feb 2025 09:46:59 +0000</pubDate>
				<category><![CDATA[機器學習筆記]]></category>
		<category><![CDATA[colab]]></category>
		<guid isPermaLink="false">https://stackoverflow.max-everyday.com/?p=6456</guid>

					<description><![CDATA[在 Google Colab 中，GPU 記憶體...]]></description>
										<content:encoded><![CDATA[
<p>在 Google Colab 中，GPU 記憶體並不會自動釋放，尤其是當發生 <code>OutOfMemoryError</code> 時，這可能會導致內存碎片或無法釋放的記憶體。要手動重設 GPU 記憶體，有幾種方法可以嘗試：</p>



<h3 class="wp-block-heading">1. 重新啟動 Colab 內核</h3>



<p>這是最簡單且最直接的方式，可以清除所有的記憶體分配：</p>



<ul class="wp-block-list">
<li>點擊 Colab 介面上的 <strong>&#8220;Runtime&#8221;</strong>。</li>



<li>選擇 <strong>&#8220;Restart runtime&#8221;</strong>（重啟運行時）。</li>
</ul>



<p>這樣可以清除所有進程並釋放 GPU 記憶體。</p>



<h3 class="wp-block-heading">2. 手動釋放 GPU 記憶體</h3>



<p>如果你不想重啟整個內核，可以手動清除一些 GPU 記憶體。試試以下方法：</p>



<h4 class="wp-block-heading">使用 <code>torch.cuda.empty_cache()</code></h4>



<p>這個方法會清除未使用的記憶體，將它釋放回 GPU，但是不會完全重設 GPU 記憶體，這對釋放一些內存是有效的。</p>



<pre class="wp-block-code"><code>import torch
torch.cuda.empty_cache()
</code></pre>



<h4 class="wp-block-heading">釋放已經不再需要的變數</h4>



<p>如果你創建了不再需要的張量，可以顯式地刪除它們並清除內存：</p>



<pre class="wp-block-code"><code>del variable_name  # 刪除不再需要的變數
torch.cuda.empty_cache()  # 清除不再使用的內存
</code></pre>



<h4 class="wp-block-heading">使用 <code>gc.collect()</code></h4>



<p>Python 的垃圾回收器有時無法及時清理不再使用的內存，手動觸發它可以幫助釋放記憶體。</p>



<pre class="wp-block-code"><code>import gc
gc.collect()
torch.cuda.empty_cache()
</code></pre>



<h3 class="wp-block-heading">3. 使用環境變數 <code>PYTORCH_CUDA_ALLOC_CONF</code></h3>



<p>如果你在使用 PyTorch 時遇到記憶體分配問題，可以通過設置環境變數來調整 CUDA 記憶體的分配行為。這有時候可以幫助避免 GPU 記憶體碎片化。</p>



<pre class="wp-block-code"><code>import os
os.environ&#91;'PYTORCH_CUDA_ALLOC_CONF'] = 'max_split_size_mb:128'
</code></pre>



<p>這會設置 PyTorch 對內存的分配大小限制，從而減少碎片化的機會。</p>



<h3 class="wp-block-heading">4. 減少 GPU 記憶體占用</h3>



<p>在訓練模型時，若 GPU 記憶體不足，還可以考慮調整以下參數來減少內存占用：</p>



<ul class="wp-block-list">
<li><strong>減小 batch size</strong>：減少每次處理的數據量。</li>



<li><strong>減少模型大小</strong>：嘗試較小的模型架構或參數。</li>



<li><strong>混合精度訓練</strong>：使用 <code>float16</code> 精度來訓練模型，這樣可以節省大量記憶體。</li>
</ul>



<pre class="wp-block-code"><code># Example of using mixed precision
from torch.cuda.amp import autocast

with autocast():
    output = model(input)
</code></pre>



<p>通過這些步驟，你可以釋放一些 GPU 記憶體，從而避免再度發生 <code>OutOfMemoryError</code>。</p>
]]></content:encoded>
					
					<wfw:commentRss>https://stackoverflow.max-everyday.com/2025/02/colab-gpu-out-of-memory-error/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>colab 上接續訓練的步驟</title>
		<link>https://stackoverflow.max-everyday.com/2025/02/colab-sd-resume-training/</link>
					<comments>https://stackoverflow.max-everyday.com/2025/02/colab-sd-resume-training/#respond</comments>
		
		<dc:creator><![CDATA[max-stackoverflow]]></dc:creator>
		<pubDate>Fri, 28 Feb 2025 08:00:07 +0000</pubDate>
				<category><![CDATA[機器學習筆記]]></category>
		<category><![CDATA[colab]]></category>
		<category><![CDATA[stable-diffusion]]></category>
		<guid isPermaLink="false">https://stackoverflow.max-everyday.com/?p=6446</guid>

					<description><![CDATA[如果要接續訓練（Resume Training）...]]></description>
										<content:encoded><![CDATA[
<p>如果要<strong>接續訓練（Resume Training）</strong>，你需要確保以下幾點：</p>



<ol class="wp-block-list">
<li><strong>之前訓練的權重檔已儲存</strong>（通常會在 <code>OUTPUT_DIR</code> 內）。</li>



<li><strong>載入最新的 checkpoint</strong>（上次訓練時的最後一步）。</li>



<li><strong>繼續 Trainer 訓練，而不是從頭開始</strong>。</li>
</ol>



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



<h3 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f539.png" alt="🔹" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 接續訓練的完整步驟</strong></h3>



<h4 class="wp-block-heading"><strong>1&#x20e3; 掛載 Google Drive 並確認已訓練的模型</strong></h4>



<pre class="wp-block-code"><code>from google.colab import drive
import os

drive.mount('/content/drive')

# 設定 Google Drive 內的數據集與輸出目錄
OUTPUT_DIR = "/content/drive/MyDrive/AI/output/zenmaru_finetune"

# 檢查上次訓練的 checkpoint 是否存在
checkpoint_path = os.path.join(OUTPUT_DIR, "checkpoint-last")

if os.path.exists(checkpoint_path):
    print(f"&#x2705; 找到上次訓練的 checkpoint: {checkpoint_path}")
else:
    print("&#x274c; 沒有找到 checkpoint，請確認上次訓練是否有儲存！")
</code></pre>



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



<h4 class="wp-block-heading"><strong>2&#x20e3; 重新載入 Stable Diffusion 2.1 模型</strong></h4>



<pre class="wp-block-code"><code>from diffusers import StableDiffusionPipeline, UNet2DConditionModel

PRETRAINED_MODEL_NAME = "stabilityai/stable-diffusion-2-1"

# 載入上次訓練的 checkpoint，而不是從頭開始
unet = UNet2DConditionModel.from_pretrained(
    checkpoint_path,  # 這裡載入上次訓練的 checkpoint
    torch_dtype=torch.float16
).to("cuda")
</code></pre>



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



<h4 class="wp-block-heading"><strong>3&#x20e3; 設定接續訓練的參數</strong></h4>



<pre class="wp-block-code"><code>from transformers import TrainingArguments, Trainer
from datasets import load_dataset

# 設定訓練參數
training_args = TrainingArguments(
    output_dir=OUTPUT_DIR,  # 繼續存放到同一個目錄
    per_device_train_batch_size=1,
    gradient_accumulation_steps=4,  
    learning_rate=5e-6,
    max_steps=20000,  # 這裡設定新總步數（包括上次訓練的步數）
    save_strategy="steps",
    save_steps=1000,
    resume_from_checkpoint=True  # &#x2705; 啟用接續訓練
)

# 重新載入數據集
DATASET_DIR = "/content/drive/MyDrive/AI/datasets/zenmaru_dataset"
dataset = load_dataset("imagefolder", data_dir=DATASET_DIR, split="train")

# 設定 Trainer
trainer = Trainer(
    model=unet,
    args=training_args,
    train_dataset=dataset
)
</code></pre>



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



<h4 class="wp-block-heading"><strong>4&#x20e3; 繼續訓練</strong></h4>



<pre class="wp-block-code"><code>trainer.train(resume_from_checkpoint=True)  # &#x2705; 這行確保會從 checkpoint 繼續訓練
</code></pre>



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



<h3 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f539.png" alt="🔹" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 確保訓練結果不會遺失</strong></h3>



<p>建議在 Google Drive 上手動檢查 <code>/AI/output/zenmaru_finetune</code> 內是否有：</p>



<ul class="wp-block-list">
<li><code>checkpoint-last/</code> 目錄（裡面有 <code>.bin</code> 或 <code>.json</code> 檔案）。</li>



<li><code>pytorch_model.bin</code> 或 <code>.safetensors</code>（訓練後的模型）。</li>
</ul>



<p>如果你想<strong>手動儲存</strong>最新的模型：</p>



<pre class="wp-block-code"><code>trainer.save_model(OUTPUT_DIR)
</code></pre>



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



<h2 class="wp-block-heading"><strong><img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f539.png" alt="🔹" class="wp-smiley" style="height: 1em; max-height: 1em;" /> 總結</strong></h2>



<ul class="wp-block-list">
<li><strong>載入上次訓練的 checkpoint</strong>（確保 <code>checkpoint-last</code> 存在）。</li>



<li><strong>設定 <code>resume_from_checkpoint=True</code></strong> 讓訓練從中斷的地方繼續。</li>



<li><strong>開始訓練 <code>trainer.train(resume_from_checkpoint=True)</code></strong>。</li>
</ul>



<p>這樣就能在 Colab <strong>繼續 Fine-tuning</strong> 了！<img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f680.png" alt="🚀" class="wp-smiley" style="height: 1em; max-height: 1em;" /><br>你上次訓練到幾步呢？ <img src="https://s.w.org/images/core/emoji/17.0.2/72x72/1f603.png" alt="😃" class="wp-smiley" style="height: 1em; max-height: 1em;" /></p>
]]></content:encoded>
					
					<wfw:commentRss>https://stackoverflow.max-everyday.com/2025/02/colab-sd-resume-training/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>在 colab 上, 要如何下載 stabilityai/stable-diffusion-2-1</title>
		<link>https://stackoverflow.max-everyday.com/2025/02/colab-stabilityai-stable-diffusion-2-1/</link>
					<comments>https://stackoverflow.max-everyday.com/2025/02/colab-stabilityai-stable-diffusion-2-1/#respond</comments>
		
		<dc:creator><![CDATA[max-stackoverflow]]></dc:creator>
		<pubDate>Fri, 28 Feb 2025 07:28:29 +0000</pubDate>
				<category><![CDATA[機器學習筆記]]></category>
		<category><![CDATA[colab]]></category>
		<category><![CDATA[stable-diffusion]]></category>
		<guid isPermaLink="false">https://stackoverflow.max-everyday.com/?p=6440</guid>

					<description><![CDATA[在 Google Colab 上下載 stabi...]]></description>
										<content:encoded><![CDATA[
<p>在 Google Colab 上下載 <code>stabilityai/stable-diffusion-2-1</code> 預訓練模型，你可以使用 <code>diffusers</code> 函式庫提供的 <code>DiffusionPipeline.from_pretrained()</code> 方法。以下是詳細步驟與程式碼範例：</p>



<p><strong>1. 安裝必要的函式庫</strong></p>



<p>首先，確保你已經安裝了 <code>diffusers</code>、<code>transformers</code> 和 <code>torch</code> 函式庫。如果沒有，可以使用以下指令安裝：</p>



<p>Bash</p>



<pre class="wp-block-code"><code>!pip install diffusers transformers torch
</code></pre>



<p><strong>2. 下載預訓練模型</strong></p>



<p>使用 <code>DiffusionPipeline.from_pretrained()</code> 方法下載模型。這個方法會自動從 Hugging Face Model Hub 下載模型，並將其儲存在 Colab 的快取目錄中。</p>



<p>Python</p>



<pre class="wp-block-code"><code>from diffusers import DiffusionPipeline

PRETRAINED_MODEL_NAME = "stabilityai/stable-diffusion-2-1"

# 下載模型
pipeline = DiffusionPipeline.from_pretrained(PRETRAINED_MODEL_NAME)

# 將模型移動到 GPU（如果可用）
pipeline = pipeline.to("cuda")
</code></pre>



<p><strong>3. 使用模型進行推理（可選）</strong></p>



<p>下載模型後，你可以立即使用它進行圖片生成。以下是一個簡單的範例：</p>



<p>Python</p>



<pre class="wp-block-code"><code>prompt = "a futuristic cityscape, digital art"
image = pipeline(prompt).images&#91;0]

# 顯示生成的圖片
image.show()

# 或者儲存圖片
image.save("generated_image.png")
</code></pre>



<p><strong>完整程式碼範例：</strong></p>



<p>Python</p>



<pre class="wp-block-code"><code>!pip install diffusers transformers torch

from diffusers import DiffusionPipeline

PRETRAINED_MODEL_NAME = "stabilityai/stable-diffusion-2-1"

# 下載模型
pipeline = DiffusionPipeline.from_pretrained(PRETRAINED_MODEL_NAME)

# 將模型移動到 GPU（如果可用）
pipeline = pipeline.to("cuda")

prompt = "a futuristic cityscape, digital art"
image = pipeline(prompt).images&#91;0]

# 顯示生成的圖片
image.show()

# 或者儲存圖片
image.save("generated_image.png")
</code></pre>



<p><strong>注意事項：</strong></p>



<ul class="wp-block-list">
<li><strong>GPU 加速：</strong>
<ul class="wp-block-list">
<li>為了加快推理速度，建議使用 GPU。請確保你的 Colab 運行時已選擇 GPU。</li>



<li><code>pipeline.to("cuda")</code> 會將模型移動到 GPU。如果你的 Colab 沒有 GPU，請移除這行程式碼。</li>
</ul>
</li>



<li><strong>模型快取：</strong>
<ul class="wp-block-list">
<li>模型下載後會儲存在 Colab 的快取目錄中。下次運行時，如果模型已經存在，就不會重新下載。</li>
</ul>
</li>



<li><strong>Hugging Face 權杖：</strong>
<ul class="wp-block-list">
<li>某些模型可能需要 Hugging Face 權杖才能下載。如果遇到權限問題，請確保你已登入 Hugging Face，並在 Colab 中設定你的權杖。</li>
</ul>
</li>



<li><strong>記憶體問題：</strong>
<ul class="wp-block-list">
<li>Stable Diffusion 模型較大，可能需要較多的 GPU 記憶體。如果遇到記憶體不足的問題，可以嘗試使用較小的模型或降低圖片生成的大小。</li>
</ul>
</li>
</ul>



<p>希望這些資訊能幫助你在 Colab 上成功下載 <code>stabilityai/stable-diffusion-2-1</code> 模型。</p>
]]></content:encoded>
					
					<wfw:commentRss>https://stackoverflow.max-everyday.com/2025/02/colab-stabilityai-stable-diffusion-2-1/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>清空 google drive 垃圾桶的內容</title>
		<link>https://stackoverflow.max-everyday.com/2025/02/empty-google-driver-trash/</link>
					<comments>https://stackoverflow.max-everyday.com/2025/02/empty-google-driver-trash/#respond</comments>
		
		<dc:creator><![CDATA[max-stackoverflow]]></dc:creator>
		<pubDate>Tue, 11 Feb 2025 14:27:52 +0000</pubDate>
				<category><![CDATA[Python筆記]]></category>
		<category><![CDATA[colab]]></category>
		<guid isPermaLink="false">https://stackoverflow.max-everyday.com/?p=6181</guid>

					<description><![CDATA[在 colab 上訓練模型, 如果沒有定時把結果...]]></description>
										<content:encoded><![CDATA[
<p>在 colab 上訓練模型, 如果沒有定時把結果存回 google drive, 那運算時間結束時, 資料也都會消失, 大約每 10分鐘左右, 會把資料存回來一次.</p>



<p>由於 google 容量又很小, checkpoint 存太多把 google drive 裝滿, 運算結果存不進去, 資料也都會消失, 中間運算結果不介意可以刪除, 只想保留最後的幾筆.</p>



<p>透過 shell command 或 python script 刪除 google drive 上的檔案, 固定都會被移動到 trash 目錄, 所以定期要清除 trash folder, 解法:</p>



<pre class="wp-block-code"><code>from googleapiclient.discovery import build
from google.colab import auth

# 1. 身份驗證
auth.authenticate_user()

# 2. 建立 Google Drive API 服務
drive_service = build('drive', 'v3')

try:
    # 清空 google drive垃圾桶
    response = drive_service.files().emptyTrash().execute()
    #print("google drive垃圾桶已清空。")
except Exception as e:
  print(f"發生錯誤：{e}")</code></pre>



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



<p>上面程式如果是寫進 .py 的檔案, 測試不會彈出授權視窗, 在沒有授權成功的情況下, 無法清除trash can,</p>



<p>所以 step 1 &amp; step 2 要放在 colab 的 notebook 下執行, 如下圖所示:</p>


<div class="wp-block-image">
<figure class="aligncenter size-full"><img decoding="async" width="607" height="302" src="https://stackoverflow.max-everyday.com/wp-content/uploads/2025/02/2025-02-11_22-17_63.jpg?v=1739283943" alt="" class="wp-image-6183" srcset="https://stackoverflow.max-everyday.com/wp-content/uploads/2025/02/2025-02-11_22-17_63.jpg?v=1739283943 607w, https://stackoverflow.max-everyday.com/wp-content/uploads/2025/02/2025-02-11_22-17_63-600x299.jpg?v=1739283943 600w" sizes="(max-width: 607px) 100vw, 607px" /></figure>
</div>


<p>在有授權的情況下, 之後的 !python 執行 python script 的檔案, 就可以正確地清除 trash can.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://stackoverflow.max-everyday.com/2025/02/empty-google-driver-trash/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>Saving and Loading Your Model to Resume Training in PyTorch</title>
		<link>https://stackoverflow.max-everyday.com/2021/06/saving-and-loading-your-model-to-resume-training-in-pytorch/</link>
					<comments>https://stackoverflow.max-everyday.com/2021/06/saving-and-loading-your-model-to-resume-training-in-pytorch/#respond</comments>
		
		<dc:creator><![CDATA[max-stackoverflow]]></dc:creator>
		<pubDate>Sun, 06 Jun 2021 14:47:03 +0000</pubDate>
				<category><![CDATA[機器學習筆記]]></category>
		<category><![CDATA[colab]]></category>
		<guid isPermaLink="false">https://stackoverflow.max-everyday.com/?p=3779</guid>

					<description><![CDATA[使用 colab 的正確姿勢之一，就是要無縫的接...]]></description>
										<content:encoded><![CDATA[
<p>使用 colab 的正確姿勢之一，就是要無縫的接續訓練，在 pytorch resume training 的方法如下。</p>



<h2 class="wp-block-heading">Saving a Checkpoint</h2>



<pre class="wp-block-preformatted">import torch
import shutil
def save_ckp(state, is_best, checkpoint_dir, best_model_dir):
     f_path = checkpoint_dir / 'checkpoint.pt'
     torch.save(state, f_path)
     if is_best:
         best_fpath = best_model_dir / 'best_model.pt'
         shutil.copyfile(f_path, best_fpath)

checkpoint = {
     'epoch': epoch + 1,
     'state_dict': model.state_dict(),
     'optimizer': optimizer.state_dict()
 }
save_ckp(checkpoint, is_best, checkpoint_dir, model_dir)</pre>



<p>附註：有些人會使用 .pth 為副檔名。</p>



<hr class="wp-block-separator"/>



<h2 class="wp-block-heading">Loading a checkpoint</h2>



<pre class="wp-block-preformatted">def load_ckp(checkpoint_fpath, model, optimizer):
     checkpoint = torch.load(checkpoint_fpath)
     model.load_state_dict(checkpoint['state_dict'])
     optimizer.load_state_dict(checkpoint['optimizer'])
     return model, optimizer, checkpoint['epoch']

model = MyModel(*args, **kwargs)
optimizer = optim.Adam(model.parameters(), lr=learning_rate)
ckp_path = "path/to/checkpoint/checkpoint.pt"
model, optimizer, start_epoch = load_ckp(ckp_path, model, optimizer)</pre>



<hr class="wp-block-separator"/>



<p>資料來源：<br><a href="https://medium.com/analytics-vidhya/saving-and-loading-your-model-to-resume-training-in-pytorch-cb687352fa61">https://medium.com/analytics-vidhya/saving-and-loading-your-model-to-resume-training-in-pytorch-cb687352fa61</a></p>
]]></content:encoded>
					
					<wfw:commentRss>https://stackoverflow.max-everyday.com/2021/06/saving-and-loading-your-model-to-resume-training-in-pytorch/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>[Pytorch] GPU 與 CPU 的切換</title>
		<link>https://stackoverflow.max-everyday.com/2021/06/pytorch-gpu-cpu-device-switch/</link>
					<comments>https://stackoverflow.max-everyday.com/2021/06/pytorch-gpu-cpu-device-switch/#respond</comments>
		
		<dc:creator><![CDATA[max-stackoverflow]]></dc:creator>
		<pubDate>Sat, 05 Jun 2021 10:01:03 +0000</pubDate>
				<category><![CDATA[機器學習筆記]]></category>
		<category><![CDATA[colab]]></category>
		<guid isPermaLink="false">https://stackoverflow.max-everyday.com/?p=3774</guid>

					<description><![CDATA[使用 google colab 執行了幾個小時後...]]></description>
										<content:encoded><![CDATA[
<p>使用 google colab 執行了幾個小時後，就彈出這一個畫面，說不能用 GPU 了。</p>



<figure class="wp-block-image size-large"><img decoding="async" width="370" height="201" src="https://stackoverflow.max-everyday.com/wp-content/uploads/2021/06/Screen-Shot-2021-06-05-at-4.20.04-PM.png" alt="" class="wp-image-3776"/></figure>



<p>Google 的「𥇧解詳情」：<br><a href="https://research.google.com/colaboratory/faq.html#usage-limits">https://research.google.com/colaboratory/faq.html#usage-limits</a></p>



<p><strong>What are the usage limits of Colab?</strong></p>



<p>Colab is able to provide free resources in part by having dynamic usage limits that sometimes fluctuate, and by not providing guaranteed or unlimited resources. This means that overall usage limits as well as idle timeout periods, maximum VM lifetime, GPU types available, and other factors vary over time. Colab does not publish these limits, in part because they can (and sometimes do) vary quickly.</p>



<p>GPUs and TPUs are sometimes prioritized for users who use Colab interactively rather than for long-running computations, or for users who have recently used less resources in Colab. As a result, users who use Colab for long-running computations, or users who have recently used more resources in Colab, are more likely to run into usage limits and have their access to GPUs and TPUs temporarily restricted. Users with high computational needs may be interested in using Colab’s UI with a&nbsp;<a href="https://research.google.com/colaboratory/local-runtimes.html">local runtime</a>&nbsp;running on their own hardware. Users interested in having higher and more stable usage limits may be interested in&nbsp;<a href="http://colab.research.google.com/signup?utm_source=faq&amp;utm_medium=link&amp;utm_campaign=what_are_usage_limits">Colab Pro</a>.</p>



<hr class="wp-block-separator"/>



<p>只好切換目前程式，改用 CPU，如果沒有調整程式，直接再執行一次會顯示下面的錯誤訊息：</p>



<pre class="wp-block-preformatted">File "/Library/Frameworks/Python.framework/Versions/3.9/lib/python3.9/site-packages/torch/serialization.py", line 135, in validate_cuda_device
     raise RuntimeError('Attempting to deserialize object on a CUDA '
 RuntimeError: Attempting to deserialize object on a CUDA device but torch.cuda.is_available() is False. If you are running on a CPU-only machine, please use torch.load with map_location=torch.device('cpu') to map your storages to the CPU.</pre>



<hr class="wp-block-separator"/>



<p>切換的方式，滿簡單的，找到 torch.load 再增加參數：</p>



<pre id="block-aa2e1c74-4fcc-4e77-9d6d-9fcdb20427c0" class="wp-block-preformatted">map_location=torch.device('cpu')</pre>



<p>問題就解決了，相關的語法：<br><a href="https://pytorch.org/tutorials/beginner/saving_loading_models.html">https://pytorch.org/tutorials/beginner/saving_loading_models.html</a></p>



<p>When it comes to saving and loading models, there are three core functions to be familiar with:</p>



<ol class="wp-block-list"><li><a href="https://pytorch.org/docs/stable/torch.html?highlight=save#torch.save">torch.save</a>: Saves a serialized object to disk. This function uses Python’s&nbsp;<a href="https://docs.python.org/3/library/pickle.html">pickle</a>&nbsp;utility for serialization. Models, tensors, and dictionaries of all kinds of objects can be saved using this function.</li><li><a href="https://pytorch.org/docs/stable/torch.html?highlight=torch%20load#torch.load">torch.load</a>: Uses&nbsp;<a href="https://docs.python.org/3/library/pickle.html">pickle</a>’s unpickling facilities to deserialize pickled object files to memory. This function also facilitates the device to load the data into (see&nbsp;<a href="https://pytorch.org/tutorials/beginner/saving_loading_models.html#saving-loading-model-across-devices">Saving &amp; Loading Model Across Devices</a>).</li><li><a href="https://pytorch.org/docs/stable/nn.html?highlight=load_state_dict#torch.nn.Module.load_state_dict">torch.nn.Module.load_state_dict</a>: Loads a model’s parameter dictionary using a deserialized&nbsp;<em>state_dict</em>. For more information on&nbsp;<em>state_dict</em>, see&nbsp;<a href="https://pytorch.org/tutorials/beginner/saving_loading_models.html#what-is-a-state-dict">What is a state_dict?</a>.</li></ol>



<p><strong>Contents:</strong></p>



<ul class="wp-block-list"><li><a href="https://pytorch.org/tutorials/beginner/saving_loading_models.html#what-is-a-state-dict">What is a state_dict?</a></li><li><a href="https://pytorch.org/tutorials/beginner/saving_loading_models.html#saving-loading-model-for-inference">Saving &amp; Loading Model for Inference</a></li><li><a href="https://pytorch.org/tutorials/beginner/saving_loading_models.html#saving-loading-a-general-checkpoint-for-inference-and-or-resuming-training">Saving &amp; Loading a General Checkpoint</a></li><li><a href="https://pytorch.org/tutorials/beginner/saving_loading_models.html#saving-multiple-models-in-one-file">Saving Multiple Models in One File</a></li><li><a href="https://pytorch.org/tutorials/beginner/saving_loading_models.html#warmstarting-model-using-parameters-from-a-different-model">Warmstarting Model Using Parameters from a Different Model</a></li><li><a href="https://pytorch.org/tutorials/beginner/saving_loading_models.html#saving-loading-model-across-devices">Saving &amp; Loading Model Across Devices</a></li></ul>



<h2 class="wp-block-heading">What is a&nbsp;<code>state_dict</code>?</h2>



<p>In PyTorch, the learnable parameters (i.e.&nbsp;weights and biases) of an&nbsp;<code>torch.nn.Module</code>&nbsp;model are contained in the model’s&nbsp;<em>parameters</em>&nbsp;(accessed with&nbsp;<code>model.parameters()</code>). A&nbsp;<em>state_dict</em>&nbsp;is simply a Python dictionary object that maps each layer to its parameter tensor. Note that only layers with learnable parameters (convolutional layers, linear layers, etc.) and registered buffers (batchnorm’s running_mean) have entries in the model’s&nbsp;<em>state_dict</em>. Optimizer objects (<code>torch.optim</code>) also have a&nbsp;<em>state_dict</em>, which contains information about the optimizer’s state, as well as the hyperparameters used.</p>



<p>Because&nbsp;<em>state_dict</em>&nbsp;objects are Python dictionaries, they can be easily saved, updated, altered, and restored, adding a great deal of modularity to PyTorch models and optimizers.</p>



<h3 class="wp-block-heading">Example:</h3>



<p>Let’s take a look at the&nbsp;<em>state_dict</em>&nbsp;from the simple model used in the&nbsp;<a href="https://pytorch.org/tutorials/beginner/blitz/cifar10_tutorial.html#sphx-glr-beginner-blitz-cifar10-tutorial-py">Training a classifier</a>&nbsp;tutorial.</p>



<pre id="codecell0" class="wp-block-preformatted"><em># Define model</em>
<strong>class</strong> <strong>TheModelClass</strong><strong>(</strong><strong>nn</strong><strong>.</strong><strong>Module</strong><strong>):</strong>
    <strong>def</strong> __init__<strong>(</strong>self<strong>):</strong>
        super<strong>(</strong><strong>TheModelClass</strong><strong>,</strong> self<strong>)</strong><strong>.</strong>__init__<strong>()</strong>
        self<strong>.</strong><strong>conv1</strong> <strong>=</strong> <strong>nn</strong><strong>.</strong><strong>Conv2d</strong><strong>(</strong>3<strong>,</strong> 6<strong>,</strong> 5<strong>)</strong>
        self<strong>.</strong><strong>pool</strong> <strong>=</strong> <strong>nn</strong><strong>.</strong><strong>MaxPool2d</strong><strong>(</strong>2<strong>,</strong> 2<strong>)</strong>
        self<strong>.</strong><strong>conv2</strong> <strong>=</strong> <strong>nn</strong><strong>.</strong><strong>Conv2d</strong><strong>(</strong>6<strong>,</strong> 16<strong>,</strong> 5<strong>)</strong>
        self<strong>.</strong><strong>fc1</strong> <strong>=</strong> <strong>nn</strong><strong>.</strong><strong>Linear</strong><strong>(</strong>16 <strong>*</strong> 5 <strong>*</strong> 5<strong>,</strong> 120<strong>)</strong>
        self<strong>.</strong><strong>fc2</strong> <strong>=</strong> <strong>nn</strong><strong>.</strong><strong>Linear</strong><strong>(</strong>120<strong>,</strong> 84<strong>)</strong>
        self<strong>.</strong><strong>fc3</strong> <strong>=</strong> <strong>nn</strong><strong>.</strong><strong>Linear</strong><strong>(</strong>84<strong>,</strong> 10<strong>)</strong>

    <strong>def</strong> <strong>forward</strong><strong>(</strong>self<strong>,</strong> <strong>x</strong><strong>):</strong>
        <strong>x</strong> <strong>=</strong> self<strong>.</strong><strong>pool</strong><strong>(</strong><strong>F</strong><strong>.</strong><strong>relu</strong><strong>(</strong>self<strong>.</strong><strong>conv1</strong><strong>(</strong><strong>x</strong><strong>)))</strong>
        <strong>x</strong> <strong>=</strong> self<strong>.</strong><strong>pool</strong><strong>(</strong><strong>F</strong><strong>.</strong><strong>relu</strong><strong>(</strong>self<strong>.</strong><strong>conv2</strong><strong>(</strong><strong>x</strong><strong>)))</strong>
        <strong>x</strong> <strong>=</strong> <strong>x</strong><strong>.</strong><strong>view</strong><strong>(</strong><strong>-</strong>1<strong>,</strong> 16 <strong>*</strong> 5 <strong>*</strong> 5<strong>)</strong>
        <strong>x</strong> <strong>=</strong> <strong>F</strong><strong>.</strong><strong>relu</strong><strong>(</strong>self<strong>.</strong><strong>fc1</strong><strong>(</strong><strong>x</strong><strong>))</strong>
        <strong>x</strong> <strong>=</strong> <strong>F</strong><strong>.</strong><strong>relu</strong><strong>(</strong>self<strong>.</strong><strong>fc2</strong><strong>(</strong><strong>x</strong><strong>))</strong>
        <strong>x</strong> <strong>=</strong> self<strong>.</strong><strong>fc3</strong><strong>(</strong><strong>x</strong><strong>)</strong>
        <strong>return</strong> <strong>x</strong>

<em># Initialize model</em>
<strong>model</strong> <strong>=</strong> <strong>TheModelClass</strong><strong>()</strong>

<em># Initialize optimizer</em>
<strong>optimizer</strong> <strong>=</strong> <strong>optim</strong><strong>.</strong><strong>SGD</strong><strong>(</strong><strong>model</strong><strong>.</strong><strong>parameters</strong><strong>(),</strong> <strong>lr</strong><strong>=</strong>0.001<strong>,</strong> <strong>momentum</strong><strong>=</strong>0.9<strong>)</strong>

<em># Print model's state_dict</em>
print<strong>(</strong>"Model's state_dict:"<strong>)</strong>
<strong>for</strong> <strong>param_tensor</strong> <strong>in</strong> <strong>model</strong><strong>.</strong><strong>state_dict</strong><strong>():</strong>
    print<strong>(</strong><strong>param_tensor</strong><strong>,</strong> "\t"<strong>,</strong> <strong>model</strong><strong>.</strong><strong>state_dict</strong><strong>()[</strong><strong>param_tensor</strong><strong>]</strong><strong>.</strong><strong>size</strong><strong>())</strong>

<em># Print optimizer's state_dict</em>
print<strong>(</strong>"Optimizer's state_dict:"<strong>)</strong>
<strong>for</strong> <strong>var_name</strong> <strong>in</strong> <strong>optimizer</strong><strong>.</strong><strong>state_dict</strong><strong>():</strong>
    print<strong>(</strong><strong>var_name</strong><strong>,</strong> "\t"<strong>,</strong> <strong>optimizer</strong><strong>.</strong><strong>state_dict</strong><strong>()[</strong><strong>var_name</strong><strong>])</strong>
</pre>



<p><a></a></p>



<p><strong>Output:</strong></p>



<pre id="codecell1" class="wp-block-preformatted"><strong>Model</strong>'s state_dict:
<strong>conv1</strong><strong>.</strong><strong>weight</strong>     <strong>torch</strong><strong>.</strong><strong>Size</strong><strong>([</strong>6<strong>,</strong> 3<strong>,</strong> 5<strong>,</strong> 5<strong>])</strong>
<strong>conv1</strong><strong>.</strong><strong>bias</strong>   <strong>torch</strong><strong>.</strong><strong>Size</strong><strong>([</strong>6<strong>])</strong>
<strong>conv2</strong><strong>.</strong><strong>weight</strong>     <strong>torch</strong><strong>.</strong><strong>Size</strong><strong>([</strong>16<strong>,</strong> 6<strong>,</strong> 5<strong>,</strong> 5<strong>])</strong>
<strong>conv2</strong><strong>.</strong><strong>bias</strong>   <strong>torch</strong><strong>.</strong><strong>Size</strong><strong>([</strong>16<strong>])</strong>
<strong>fc1</strong><strong>.</strong><strong>weight</strong>   <strong>torch</strong><strong>.</strong><strong>Size</strong><strong>([</strong>120<strong>,</strong> 400<strong>])</strong>
<strong>fc1</strong><strong>.</strong><strong>bias</strong>     <strong>torch</strong><strong>.</strong><strong>Size</strong><strong>([</strong>120<strong>])</strong>
<strong>fc2</strong><strong>.</strong><strong>weight</strong>   <strong>torch</strong><strong>.</strong><strong>Size</strong><strong>([</strong>84<strong>,</strong> 120<strong>])</strong>
<strong>fc2</strong><strong>.</strong><strong>bias</strong>     <strong>torch</strong><strong>.</strong><strong>Size</strong><strong>([</strong>84<strong>])</strong>
<strong>fc3</strong><strong>.</strong><strong>weight</strong>   <strong>torch</strong><strong>.</strong><strong>Size</strong><strong>([</strong>10<strong>,</strong> 84<strong>])</strong>
<strong>fc3</strong><strong>.</strong><strong>bias</strong>     <strong>torch</strong><strong>.</strong><strong>Size</strong><strong>([</strong>10<strong>])</strong>

<strong>Optimizer</strong>'s state_dict:
<strong>state</strong>    <strong>{}</strong>
<strong>param_groups</strong>     <strong>[{</strong>'lr'<strong>:</strong> 0.001<strong>,</strong> 'momentum'<strong>:</strong> 0.9<strong>,</strong> 'dampening'<strong>:</strong> 0<strong>,</strong> 'weight_decay'<strong>:</strong> 0<strong>,</strong> 'nesterov'<strong>:</strong> <strong>False</strong><strong>,</strong> 'params'<strong>:</strong> <strong>[</strong>4675713712<strong>,</strong> 4675713784<strong>,</strong> 4675714000<strong>,</strong> 4675714072<strong>,</strong> 4675714216<strong>,</strong> 4675714288<strong>,</strong> 4675714432<strong>,</strong> 4675714504<strong>,</strong> 4675714648<strong>,</strong> 4675714720<strong>]}]</strong>
</pre>



<p><a></a></p>



<h2 class="wp-block-heading">Saving &amp; Loading Model for Inference</h2>



<h3 class="wp-block-heading">Save/Load&nbsp;<code>state_dict</code>&nbsp;(Recommended)</h3>



<p><strong>Save:</strong></p>



<pre id="codecell2" class="wp-block-preformatted"><strong>torch</strong><strong>.</strong><strong>save</strong><strong>(</strong><strong>model</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong> <strong>PATH</strong><strong>)</strong>
</pre>



<p><a></a></p>



<p><strong>Load:</strong></p>



<pre id="codecell3" class="wp-block-preformatted"><strong>model</strong> <strong>=</strong> <strong>TheModelClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>
<strong>model</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>torch</strong><strong>.</strong><strong>load</strong><strong>(</strong><strong>PATH</strong><strong>))</strong>
<strong>model</strong><strong>.</strong><strong>eval</strong><strong>()</strong>
</pre>



<p><a></a></p>



<p>NOTE</p>



<p>The 1.6 release of PyTorch switched&nbsp;<code>torch.save</code>&nbsp;to use a new zipfile-based file format.&nbsp;<code>torch.load</code>&nbsp;still retains the ability to load files in the old format. If for any reason you want&nbsp;<code>torch.save</code>&nbsp;to use the old format, pass the kwarg&nbsp;<code>_use_new_zipfile_serialization=False</code>.</p>



<p>When saving a model for inference, it is only necessary to save the trained model’s learned parameters. Saving the model’s&nbsp;<em>state_dict</em>&nbsp;with the&nbsp;<code>torch.save()</code>&nbsp;function will give you the most flexibility for restoring the model later, which is why it is the recommended method for saving models.</p>



<p>A common PyTorch convention is to save models using either a&nbsp;<code>.pt</code>&nbsp;or&nbsp;<code>.pth</code>&nbsp;file extension.</p>



<p>Remember that you must call&nbsp;<code>model.eval()</code>&nbsp;to set dropout and batch normalization layers to evaluation mode before running inference. Failing to do this will yield inconsistent inference results.</p>



<p>NOTE</p>



<p>Notice that the&nbsp;<code>load_state_dict()</code>&nbsp;function takes a dictionary object, NOT a path to a saved object. This means that you must deserialize the saved&nbsp;<em>state_dict</em>&nbsp;before you pass it to the&nbsp;<code>load_state_dict()</code>&nbsp;function. For example, you CANNOT load using&nbsp;<code>model.load_state_dict(PATH)</code>.</p>



<p>NOTE</p>



<p>If you only plan to keep the best performing model (according to the acquired validation loss), don’t forget that&nbsp;<code>best_model_state&nbsp;=&nbsp;model.state_dict()</code>&nbsp;returns a reference to the state and not its copy! You must serialize&nbsp;<code>best_model_state</code>&nbsp;or use&nbsp;<code>best_model_state&nbsp;=&nbsp;deepcopy(model.state_dict())</code>&nbsp;otherwise your best&nbsp;<code>best_model_state</code>&nbsp;will keep getting updated by the subsequent training iterations. As a result, the final model state will be the state of the overfitted model.</p>



<h3 class="wp-block-heading">Save/Load Entire Model</h3>



<p><strong>Save:</strong></p>



<pre id="codecell4" class="wp-block-preformatted"><strong>torch</strong><strong>.</strong><strong>save</strong><strong>(</strong><strong>model</strong><strong>,</strong> <strong>PATH</strong><strong>)</strong>
</pre>



<p><a></a></p>



<p><strong>Load:</strong></p>



<pre id="codecell5" class="wp-block-preformatted"><em># Model class must be defined somewhere</em>
<strong>model</strong> <strong>=</strong> <strong>torch</strong><strong>.</strong><strong>load</strong><strong>(</strong><strong>PATH</strong><strong>)</strong>
<strong>model</strong><strong>.</strong><strong>eval</strong><strong>()</strong>
</pre>



<p><a></a></p>



<p>This save/load process uses the most intuitive syntax and involves the least amount of code. Saving a model in this way will save the entire module using Python’s&nbsp;<a href="https://docs.python.org/3/library/pickle.html">pickle</a>&nbsp;module. The disadvantage of this approach is that the serialized data is bound to the specific classes and the exact directory structure used when the model is saved. The reason for this is because pickle does not save the model class itself. Rather, it saves a path to the file containing the class, which is used during load time. Because of this, your code can break in various ways when used in other projects or after refactors.</p>



<p>A common PyTorch convention is to save models using either a&nbsp;<code>.pt</code>&nbsp;or&nbsp;<code>.pth</code>&nbsp;file extension.</p>



<p>Remember that you must call&nbsp;<code>model.eval()</code>&nbsp;to set dropout and batch normalization layers to evaluation mode before running inference. Failing to do this will yield inconsistent inference results.</p>



<h2 class="wp-block-heading">Saving &amp; Loading a General Checkpoint for Inference and/or Resuming Training</h2>



<h3 class="wp-block-heading">Save:</h3>



<pre id="codecell6" class="wp-block-preformatted"><strong>torch</strong><strong>.</strong><strong>save</strong><strong>({</strong>
            'epoch'<strong>:</strong> <strong>epoch</strong><strong>,</strong>
            'model_state_dict'<strong>:</strong> <strong>model</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong>
            'optimizer_state_dict'<strong>:</strong> <strong>optimizer</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong>
            'loss'<strong>:</strong> <strong>loss</strong><strong>,</strong>
            <strong>...</strong>
            <strong>},</strong> <strong>PATH</strong><strong>)</strong>
</pre>



<p><a></a></p>



<h3 class="wp-block-heading">Load:</h3>



<pre id="codecell7" class="wp-block-preformatted"><strong>model</strong> <strong>=</strong> <strong>TheModelClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>
<strong>optimizer</strong> <strong>=</strong> <strong>TheOptimizerClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>

<strong>checkpoint</strong> <strong>=</strong> <strong>torch</strong><strong>.</strong><strong>load</strong><strong>(</strong><strong>PATH</strong><strong>)</strong>
<strong>model</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>checkpoint</strong><strong>[</strong>'model_state_dict'<strong>])</strong>
<strong>optimizer</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>checkpoint</strong><strong>[</strong>'optimizer_state_dict'<strong>])</strong>
<strong>epoch</strong> <strong>=</strong> <strong>checkpoint</strong><strong>[</strong>'epoch'<strong>]</strong>
<strong>loss</strong> <strong>=</strong> <strong>checkpoint</strong><strong>[</strong>'loss'<strong>]</strong>

<strong>model</strong><strong>.</strong><strong>eval</strong><strong>()</strong>
<em># - or -</em>
<strong>model</strong><strong>.</strong><strong>train</strong><strong>()</strong>
</pre>



<p><a></a></p>



<p>When saving a general checkpoint, to be used for either inference or resuming training, you must save more than just the model’s&nbsp;<em>state_dict</em>. It is important to also save the optimizer’s&nbsp;<em>state_dict</em>, as this contains buffers and parameters that are updated as the model trains. Other items that you may want to save are the epoch you left off on, the latest recorded training loss, external&nbsp;<code>torch.nn.Embedding</code>&nbsp;layers, etc. As a result, such a checkpoint is often 2~3 times larger than the model alone.</p>



<p>To save multiple components, organize them in a dictionary and use&nbsp;<code>torch.save()</code>&nbsp;to serialize the dictionary. A common PyTorch convention is to save these checkpoints using the&nbsp;<code>.tar</code>&nbsp;file extension.</p>



<p>To load the items, first initialize the model and optimizer, then load the dictionary locally using&nbsp;<code>torch.load()</code>. From here, you can easily access the saved items by simply querying the dictionary as you would expect.</p>



<p>Remember that you must call&nbsp;<code>model.eval()</code>&nbsp;to set dropout and batch normalization layers to evaluation mode before running inference. Failing to do this will yield inconsistent inference results. If you wish to resuming training, call&nbsp;<code>model.train()</code>&nbsp;to ensure these layers are in training mode.</p>



<h2 class="wp-block-heading">Saving Multiple Models in One File</h2>



<h3 class="wp-block-heading">Save:</h3>



<pre id="codecell8" class="wp-block-preformatted"><strong>torch</strong><strong>.</strong><strong>save</strong><strong>({</strong>
            'modelA_state_dict'<strong>:</strong> <strong>modelA</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong>
            'modelB_state_dict'<strong>:</strong> <strong>modelB</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong>
            'optimizerA_state_dict'<strong>:</strong> <strong>optimizerA</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong>
            'optimizerB_state_dict'<strong>:</strong> <strong>optimizerB</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong>
            <strong>...</strong>
            <strong>},</strong> <strong>PATH</strong><strong>)</strong>
</pre>



<p><a></a></p>



<h3 class="wp-block-heading">Load:</h3>



<pre id="codecell9" class="wp-block-preformatted"><strong>modelA</strong> <strong>=</strong> <strong>TheModelAClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>
<strong>modelB</strong> <strong>=</strong> <strong>TheModelBClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>
<strong>optimizerA</strong> <strong>=</strong> <strong>TheOptimizerAClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>
<strong>optimizerB</strong> <strong>=</strong> <strong>TheOptimizerBClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>

<strong>checkpoint</strong> <strong>=</strong> <strong>torch</strong><strong>.</strong><strong>load</strong><strong>(</strong><strong>PATH</strong><strong>)</strong>
<strong>modelA</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>checkpoint</strong><strong>[</strong>'modelA_state_dict'<strong>])</strong>
<strong>modelB</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>checkpoint</strong><strong>[</strong>'modelB_state_dict'<strong>])</strong>
<strong>optimizerA</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>checkpoint</strong><strong>[</strong>'optimizerA_state_dict'<strong>])</strong>
<strong>optimizerB</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>checkpoint</strong><strong>[</strong>'optimizerB_state_dict'<strong>])</strong>

<strong>modelA</strong><strong>.</strong><strong>eval</strong><strong>()</strong>
<strong>modelB</strong><strong>.</strong><strong>eval</strong><strong>()</strong>
<em># - or -</em>
<strong>modelA</strong><strong>.</strong><strong>train</strong><strong>()</strong>
<strong>modelB</strong><strong>.</strong><strong>train</strong><strong>()</strong>
</pre>



<p><a></a></p>



<p>When saving a model comprised of multiple&nbsp;<code>torch.nn.Modules</code>, such as a GAN, a sequence-to-sequence model, or an ensemble of models, you follow the same approach as when you are saving a general checkpoint. In other words, save a dictionary of each model’s&nbsp;<em>state_dict</em>&nbsp;and corresponding optimizer. As mentioned before, you can save any other items that may aid you in resuming training by simply appending them to the dictionary.</p>



<p>A common PyTorch convention is to save these checkpoints using the&nbsp;<code>.tar</code>&nbsp;file extension.</p>



<p>To load the models, first initialize the models and optimizers, then load the dictionary locally using&nbsp;<code>torch.load()</code>. From here, you can easily access the saved items by simply querying the dictionary as you would expect.</p>



<p>Remember that you must call&nbsp;<code>model.eval()</code>&nbsp;to set dropout and batch normalization layers to evaluation mode before running inference. Failing to do this will yield inconsistent inference results. If you wish to resuming training, call&nbsp;<code>model.train()</code>&nbsp;to set these layers to training mode.</p>



<h2 class="wp-block-heading">Warmstarting Model Using Parameters from a Different Model</h2>



<h3 class="wp-block-heading">Save:</h3>



<pre id="codecell10" class="wp-block-preformatted"><strong>torch</strong><strong>.</strong><strong>save</strong><strong>(</strong><strong>modelA</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong> <strong>PATH</strong><strong>)</strong>
</pre>



<p><a></a></p>



<h3 class="wp-block-heading">Load:</h3>



<pre id="codecell11" class="wp-block-preformatted"><strong>modelB</strong> <strong>=</strong> <strong>TheModelBClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>
<strong>modelB</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>torch</strong><strong>.</strong><strong>load</strong><strong>(</strong><strong>PATH</strong><strong>),</strong> <strong>strict</strong><strong>=</strong><strong>False</strong><strong>)</strong>
</pre>



<p><a></a></p>



<p>Partially loading a model or loading a partial model are common scenarios when transfer learning or training a new complex model. Leveraging trained parameters, even if only a few are usable, will help to warmstart the training process and hopefully help your model converge much faster than training from scratch.</p>



<p>Whether you are loading from a partial&nbsp;<em>state_dict</em>, which is missing some keys, or loading a&nbsp;<em>state_dict</em>&nbsp;with more keys than the model that you are loading into, you can set the&nbsp;<code>strict</code>&nbsp;argument to&nbsp;<strong>False</strong>&nbsp;in the&nbsp;<code>load_state_dict()</code>&nbsp;function to ignore non-matching keys.</p>



<p>If you want to load parameters from one layer to another, but some keys do not match, simply change the name of the parameter keys in the&nbsp;<em>state_dict</em>&nbsp;that you are loading to match the keys in the model that you are loading into.</p>



<h2 class="wp-block-heading">Saving &amp; Loading Model Across Devices</h2>



<h3 class="wp-block-heading">Save on GPU, Load on CPU</h3>



<p><strong>Save:</strong></p>



<pre id="codecell12" class="wp-block-preformatted"><strong>torch</strong><strong>.</strong><strong>save</strong><strong>(</strong><strong>model</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong> <strong>PATH</strong><strong>)</strong>
</pre>



<p><a></a></p>



<p><strong>Load:</strong></p>



<pre id="codecell13" class="wp-block-preformatted"><strong>device</strong> <strong>=</strong> <strong>torch</strong><strong>.</strong><strong>device</strong><strong>(</strong>'cpu'<strong>)</strong>
<strong>model</strong> <strong>=</strong> <strong>TheModelClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>
<strong>model</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>torch</strong><strong>.</strong><strong>load</strong><strong>(</strong><strong>PATH</strong><strong>,</strong> <strong>map_location</strong><strong>=</strong><strong>device</strong><strong>))</strong>
</pre>



<p><a></a></p>



<p>When loading a model on a CPU that was trained with a GPU, pass&nbsp;<code>torch.device('cpu')</code>&nbsp;to the&nbsp;<code>map_location</code>&nbsp;argument in the&nbsp;<code>torch.load()</code>&nbsp;function. In this case, the storages underlying the tensors are dynamically remapped to the CPU device using the&nbsp;<code>map_location</code>&nbsp;argument.</p>



<h3 class="wp-block-heading">Save on GPU, Load on GPU</h3>



<p><strong>Save:</strong></p>



<pre id="codecell14" class="wp-block-preformatted"><strong>torch</strong><strong>.</strong><strong>save</strong><strong>(</strong><strong>model</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong> <strong>PATH</strong><strong>)</strong>
</pre>



<p><a></a></p>



<p><strong>Load:</strong></p>



<pre id="codecell15" class="wp-block-preformatted"><strong>device</strong> <strong>=</strong> <strong>torch</strong><strong>.</strong><strong>device</strong><strong>(</strong>"cuda"<strong>)</strong>
<strong>model</strong> <strong>=</strong> <strong>TheModelClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>
<strong>model</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>torch</strong><strong>.</strong><strong>load</strong><strong>(</strong><strong>PATH</strong><strong>))</strong>
<strong>model</strong><strong>.</strong><strong>to</strong><strong>(</strong><strong>device</strong><strong>)</strong>
<em># Make sure to call input = input.to(device) on any input tensors that you feed to the model</em>
</pre>



<p><a></a></p>



<p>When loading a model on a GPU that was trained and saved on GPU, simply convert the initialized&nbsp;<code>model</code>&nbsp;to a CUDA optimized model using&nbsp;<code>model.to(torch.device('cuda'))</code>. Also, be sure to use the&nbsp;<code>.to(torch.device('cuda'))</code>&nbsp;function on all model inputs to prepare the data for the model. Note that calling&nbsp;<code>my_tensor.to(device)</code>&nbsp;returns a new copy of&nbsp;<code>my_tensor</code>&nbsp;on GPU. It does NOT overwrite&nbsp;<code>my_tensor</code>. Therefore, remember to manually overwrite tensors:&nbsp;<code>my_tensor&nbsp;=&nbsp;my_tensor.to(torch.device('cuda'))</code>.</p>



<h3 class="wp-block-heading">Save on CPU, Load on GPU</h3>



<p><strong>Save:</strong></p>



<pre id="codecell16" class="wp-block-preformatted"><strong>torch</strong><strong>.</strong><strong>save</strong><strong>(</strong><strong>model</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong> <strong>PATH</strong><strong>)</strong>
</pre>



<p><a></a></p>



<p><strong>Load:</strong></p>



<pre id="codecell17" class="wp-block-preformatted"><strong>device</strong> <strong>=</strong> <strong>torch</strong><strong>.</strong><strong>device</strong><strong>(</strong>"cuda"<strong>)</strong>
<strong>model</strong> <strong>=</strong> <strong>TheModelClass</strong><strong>(</strong><strong>*</strong><strong>args</strong><strong>,</strong> <strong>**</strong><strong>kwargs</strong><strong>)</strong>
<strong>model</strong><strong>.</strong><strong>load_state_dict</strong><strong>(</strong><strong>torch</strong><strong>.</strong><strong>load</strong><strong>(</strong><strong>PATH</strong><strong>,</strong> <strong>map_location</strong><strong>=</strong>"cuda:0"<strong>))</strong>  <em># Choose whatever GPU device number you want</em>
<strong>model</strong><strong>.</strong><strong>to</strong><strong>(</strong><strong>device</strong><strong>)</strong>
<em># Make sure to call input = input.to(device) on any input tensors that you feed to the model</em>
</pre>



<p><a></a></p>



<p>When loading a model on a GPU that was trained and saved on CPU, set the&nbsp;<code>map_location</code>&nbsp;argument in the&nbsp;<code>torch.load()</code>&nbsp;function to&nbsp;<em>cuda:device_id</em>. This loads the model to a given GPU device. Next, be sure to call&nbsp;<code>model.to(torch.device('cuda'))</code>&nbsp;to convert the model’s parameter tensors to CUDA tensors. Finally, be sure to use the&nbsp;<code>.to(torch.device('cuda'))</code>&nbsp;function on all model inputs to prepare the data for the CUDA optimized model. Note that calling&nbsp;<code>my_tensor.to(device)</code>&nbsp;returns a new copy of&nbsp;<code>my_tensor</code>&nbsp;on GPU. It does NOT overwrite&nbsp;<code>my_tensor</code>. Therefore, remember to manually overwrite tensors:&nbsp;<code>my_tensor&nbsp;=&nbsp;my_tensor.to(torch.device('cuda'))</code>.</p>



<h3 class="wp-block-heading">Saving&nbsp;<code>torch.nn.DataParallel</code>&nbsp;Models</h3>



<p><strong>Save:</strong></p>



<pre id="codecell18" class="wp-block-preformatted"><strong>torch</strong><strong>.</strong><strong>save</strong><strong>(</strong><strong>model</strong><strong>.</strong><strong>module</strong><strong>.</strong><strong>state_dict</strong><strong>(),</strong> <strong>PATH</strong><strong>)</strong>
</pre>



<p><a></a></p>



<p><strong>Load:</strong></p>



<pre id="codecell19" class="wp-block-preformatted"><em># Load to whatever device you want</em>
</pre>



<p><a></a></p>



<p><code>torch.nn.DataParallel</code>&nbsp;is a model wrapper that enables parallel GPU utilization. To save a&nbsp;<code>DataParallel</code>&nbsp;model generically, save the&nbsp;<code>model.module.state_dict()</code>. This way, you have the flexibility to load the model any way you want to any device you want.</p>
]]></content:encoded>
					
					<wfw:commentRss>https://stackoverflow.max-everyday.com/2021/06/pytorch-gpu-cpu-device-switch/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>測試Colab提供的免費TPU</title>
		<link>https://stackoverflow.max-everyday.com/2021/06/colab-tpu-test/</link>
					<comments>https://stackoverflow.max-everyday.com/2021/06/colab-tpu-test/#respond</comments>
		
		<dc:creator><![CDATA[max-stackoverflow]]></dc:creator>
		<pubDate>Fri, 04 Jun 2021 17:58:22 +0000</pubDate>
				<category><![CDATA[機器學習筆記]]></category>
		<category><![CDATA[colab]]></category>
		<guid isPermaLink="false">https://stackoverflow.max-everyday.com/?p=3768</guid>

					<description><![CDATA[從其他網頁上收集到的資訊來看，應該多去使用免費的...]]></description>
										<content:encoded><![CDATA[
<p>從其他網頁上收集到的資訊來看，應該多去使用免費的TPU，因為執行的時間有可能只需要原本的訓練時間的 1/3， 缺點是程式碼需要一點點的微調。參考網頁說明：</p>



<p>Colab提供了免費TPU<br><a href="https://www.itread01.com/elpqhk.html">https://www.itread01.com/elpqhk.html</a></p>



<p>參考性佳的範例：<br>Getting Started with PyTorch on Cloud TPUs<br><a href="https://medium.com/pytorch/get-started-with-pytorch-cloud-tpus-and-colab-a24757b8f7fc">https://medium.com/pytorch/get-started-with-pytorch-cloud-tpus-and-colab-a24757b8f7fc</a></p>



<h2 class="wp-block-heading">Get started with our Colab Tutorials</h2>



<ul class="wp-block-list"><li><a href="https://colab.research.google.com/github/pytorch/xla/blob/master/contrib/colab/getting-started.ipynb">Getting Started with PyTorch on Cloud TPUs</a></li><li><a href="https://colab.research.google.com/github/pytorch/xla/blob/master/contrib/colab/single-core-alexnet-fashion-mnist.ipynb">Training AlexNet on Fashion MNIST with a single Cloud TPU Core</a></li><li><a href="https://colab.research.google.com/github/pytorch/xla/blob/master/contrib/colab/multi-core-alexnet-fashion-mnist.ipynb">Training AlexNet on Fashion MNIST with multiple Cloud TPU Cores</a></li><li><a href="https://colab.research.google.com/github/pytorch/xla/blob/master/contrib/colab/style_transfer_inference.ipynb">Fast Neural Style Transfer (NeurIPS 2019 Demo)</a></li><li><a href="https://colab.research.google.com/github/pytorch/xla/blob/master/contrib/colab/mnist-training.ipynb">Training A Simple Convolutional Network on MNIST</a></li><li><a href="https://colab.research.google.com/github/pytorch/xla/blob/master/contrib/colab/resnet18-training.ipynb">Training a ResNet18 Network on CIFAR10</a></li><li><a href="https://colab.research.google.com/github/pytorch/xla/blob/master/contrib/colab/resnet50-inference.ipynb">ImageNet Inference with ResNet50</a></li><li><a href="https://colab.research.google.com/github/pytorch/xla/blob/master/contrib/colab/pytorch-xla-profiling-colab.ipynb">PyTorch/XLA Performance Profiling</a></li></ul>



<p><em>Note</em>: These colab notebooks typically run on small machines (the Compute VMs, which runs the input pipeline) and training is often bottlenecked on the small Compute VM machines. For optimal performance create a GCP VM and TPU pair following our GCP Tutorials:</p>



<ul class="wp-block-list"><li><a href="https://cloud.google.com/tpu/docs/tutorials/transformer-pytorch">Training FairSeq Transformer on Cloud TPUs</a></li><li><a href="https://cloud.google.com/tpu/docs/tutorials/resnet-pytorch">Training Resnet50 on Cloud TPUs</a></li><li><a href="https://cloud.google.com/tpu/docs/tutorials/pytorch-pod">Training PyTorch models on Cloud TPU Pods</a></li></ul>



<hr class="wp-block-separator"/>



<p>實際測試結果，在 import xla_model 時，可以看到去初始化 TPU的訊息，最後成功取得 TPU 資源。</p>



<p>TPU 與 cuda 似乎是不同的世界，所以 CUDA 沒被啟用。</p>



<figure class="wp-block-image size-large"><img loading="lazy" decoding="async" width="1024" height="506" src="https://stackoverflow.max-everyday.com/wp-content/uploads/2021/06/Screen-Shot-2021-06-05-at-1.55.37-AM-1024x506.png?v=1622829375" alt="" class="wp-image-3770" srcset="https://stackoverflow.max-everyday.com/wp-content/uploads/2021/06/Screen-Shot-2021-06-05-at-1.55.37-AM-1024x506.png?v=1622829375 1024w, https://stackoverflow.max-everyday.com/wp-content/uploads/2021/06/Screen-Shot-2021-06-05-at-1.55.37-AM-600x297.png?v=1622829375 600w, https://stackoverflow.max-everyday.com/wp-content/uploads/2021/06/Screen-Shot-2021-06-05-at-1.55.37-AM-768x380.png?v=1622829375 768w, https://stackoverflow.max-everyday.com/wp-content/uploads/2021/06/Screen-Shot-2021-06-05-at-1.55.37-AM-1536x759.png?v=1622829375 1536w, https://stackoverflow.max-everyday.com/wp-content/uploads/2021/06/Screen-Shot-2021-06-05-at-1.55.37-AM.png?v=1622829375 1740w" sizes="(max-width: 1024px) 100vw, 1024px" /></figure>



<p></p>
]]></content:encoded>
					
					<wfw:commentRss>https://stackoverflow.max-everyday.com/2021/06/colab-tpu-test/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
		<item>
		<title>[PyTorch] output with shape [1, 28, 28] doesn&#8217;t match the broadcast shape [3, 28, 28]</title>
		<link>https://stackoverflow.max-everyday.com/2021/06/pytorch-output-with-shape-1-28-28-doesnt-match-the-broadcast-shape-3-28-28/</link>
					<comments>https://stackoverflow.max-everyday.com/2021/06/pytorch-output-with-shape-1-28-28-doesnt-match-the-broadcast-shape-3-28-28/#respond</comments>
		
		<dc:creator><![CDATA[max-stackoverflow]]></dc:creator>
		<pubDate>Thu, 03 Jun 2021 20:42:56 +0000</pubDate>
				<category><![CDATA[Python筆記]]></category>
		<category><![CDATA[機器學習筆記]]></category>
		<category><![CDATA[colab]]></category>
		<category><![CDATA[image]]></category>
		<category><![CDATA[Python]]></category>
		<guid isPermaLink="false">https://stackoverflow.max-everyday.com/?p=3766</guid>

					<description><![CDATA[會產生這一個錯誤，原因是圖片的格式造成，是彩色還...]]></description>
										<content:encoded><![CDATA[
<p>會產生這一個錯誤，原因是圖片的格式造成，是彩色還是灰階（黑白）圖片。</p>



<p>Let me clarify, if the img has three channels, you should have three number for mean, for example, img is RGB, mean is [0.5, 0.5, 0.5], the normalize result is R * 0.5, G * 0.5, B * 0.5. If img is grey type that only one channel, so mean should be [0.5], the normalize result is R * 0.5</p>



<p>資料來源：<br><a href="https://github.com/yunjey/pytorch-tutorial/issues/161">https://github.com/yunjey/pytorch-tutorial/issues/161</a></p>



<hr class="wp-block-separator"/>



<p>解法很多，需要配合程式變成彩色，或修改程式的流程。如果是在python 裡使用 PIL 讀取圖片，轉換方式如下：</p>



<pre class="wp-block-code"><code>img = Image.open(GIF_FILENAME)
rgbimg = Image.new("RGBA", img.size)
rgbimg.paste(img)
rgbimg.save('foo.jpg')</code></pre>



<p></p>
]]></content:encoded>
					
					<wfw:commentRss>https://stackoverflow.max-everyday.com/2021/06/pytorch-output-with-shape-1-28-28-doesnt-match-the-broadcast-shape-3-28-28/feed/</wfw:commentRss>
			<slash:comments>0</slash:comments>
		
		
			</item>
	</channel>
</rss>
