Text-to-Image
Diffusers
Safetensors
English
Chinese
QwenImage21Pipeline
sdnq
int4
uint4
image-generation
image-editing
apple-silicon
8-bit precision
Instructions to use ixim/Image21-INT4 with libraries, inference providers, notebooks, and local apps. Follow these links to get started.
- Libraries
- Diffusers
How to use ixim/Image21-INT4 with Diffusers:
pip install -U diffusers transformers accelerate
import torch from diffusers import DiffusionPipeline # switch to "mps" for apple devices pipe = DiffusionPipeline.from_pretrained("ixim/Image21-INT4", dtype=torch.bfloat16, device_map="cuda") prompt = "Astronaut in a jungle, cold color palette, muted colors, detailed, 8k" image = pipe(prompt).images[0] - Notebooks
- Google Colab
- Kaggle
- Local Apps Settings
- Draw Things
- DiffusionBee
Download scripts/model_card.py from ixim/Image21-INT4: direct link, hf CLI and curl.
- Browser
- Download file 5.48 kB
-
https://huggingface.co/ixim/Image21-INT4/resolve/main/scripts/model_card.py
- Command line
-
hf download hf://ixim/Image21-INT4/scripts/model_card.py
-
curl -L -o model_card.py https://huggingface.co/ixim/Image21-INT4/resolve/main/scripts/model_card.py
5.48 kB
| """Fill the model card from measured records.""" | |
| import json | |
| from pathlib import Path | |
| from scripts.report import load_records | |
| def _tr(platform, english, chinese): | |
| return chinese if platform == 'modelscope' else english | |
| def _table(headers, rows): | |
| lines = ['| ' + ' | '.join(headers) + ' |', '|' + '|'.join('---' for _ in headers) + '|'] | |
| lines.extend('| ' + ' | '.join(row) + ' |' for row in rows) | |
| return '\n'.join(lines) | |
| def render(evaluation, platform, summary, vram_row): | |
| evaluation = Path(evaluation) | |
| baseline = load_records(evaluation / 'bf16') | |
| env = json.loads((evaluation / 'bf16/environment.json').read_text(encoding='utf-8')) | |
| vram_env = json.loads((evaluation / 'vram8/environment.json').read_text(encoding='utf-8')) | |
| notes = (evaluation / 'qualitative.md').read_text(encoding='utf-8').strip() | |
| pairs = sorted(baseline, key=lambda key: (key[0], key[1])) | |
| metric_rows = [] | |
| comparison = {} | |
| import csv | |
| with (evaluation / 'comparison.csv').open(encoding='utf-8', newline='') as handle: | |
| for row in csv.DictReader(handle): | |
| comparison[(row['case_id'], int(row['seed']))] = row | |
| for case_id, seed in pairs: | |
| row = comparison[(case_id, seed)] | |
| metric_rows.append([case_id, str(seed), f'{float(row["bf16_seconds"]):.2f}', | |
| f'{float(row["int4_seconds"]):.2f}', | |
| f'{float(row["bf16_peak_allocated_gib"]):.2f}', | |
| f'{float(row["int4_peak_allocated_gib"]):.2f}', | |
| f'{float(row["rgb_mae_white"]):.4f}']) | |
| int4_records = load_records(evaluation / 'int4') | |
| samples = [] | |
| for case_id, seed in pairs: | |
| left = f'evaluation/bf16/{baseline[(case_id, seed)]["image"]}' | |
| right = f'evaluation/int4/{int4_records[(case_id, seed)]["image"]}' | |
| prompt = baseline[(case_id, seed)]['prompt'] | |
| samples.append('\n'.join([ | |
| f'### {case_id} / seed {seed}', '', | |
| prompt, '', | |
| _table(['BF16', 'INT4'], [[f'', f'']]), | |
| ''])) | |
| packages = '\n'.join(f'| {name} | {version} |' for name, version in env['packages'].items()) | |
| cap_gib = vram_env['memory_cap']['cap_gib'] | |
| details = '\n'.join([ | |
| _tr(platform, '### Measured comparison', '### 实测对比'), '', | |
| _tr(platform, | |
| f'{summary["pairs"]} pairs, {summary["width"]}×{summary["height"]}, {summary["steps"]} steps, ' | |
| f'CFG 1, KV cache on, model CPU offload, one excluded warmup. Host: {env["gpu"]}.', | |
| f'{summary["pairs"]} 对,{summary["width"]}×{summary["height"]},{summary["steps"]} 步,' | |
| f'CFG 1,开启 KV cache,model CPU offload,各有一次不计入的预热。机器:{env["gpu"]}。'), | |
| '', | |
| _table(['', 'BF16', 'INT4'], [ | |
| [_tr(platform, 'Weight files (decimal GB)', '权重体积(十进制 GB)'), | |
| f'{summary["bf16_weight_bytes"]/1e9:.3f}', f'{summary["int4_weight_bytes"]/1e9:.3f}'], | |
| [_tr(platform, 'Mean call latency (s)', '平均调用耗时(秒)'), | |
| f'{summary["bf16_mean_seconds"]:.2f}', f'{summary["int4_mean_seconds"]:.2f}'], | |
| [_tr(platform, 'Maximum allocated CUDA memory (GiB)', '已分配 CUDA 显存最高值(GiB)'), | |
| f'{summary["bf16_max_allocated_gib"]:.2f}', f'{summary["int4_max_allocated_gib"]:.2f}'], | |
| ]), | |
| '', | |
| _table(['Case', 'Seed', 'BF16 s', 'INT4 s', 'BF16 GiB', 'INT4 GiB', 'RGB MAE'], metric_rows), | |
| '', | |
| _tr(platform, '### Package versions', '### 软件包版本'), '', | |
| '| Package | Version |', '|---|---|', packages, '', | |
| _tr(platform, '### Visual inspection', '### 目视检查'), '', | |
| notes, '', | |
| _tr(platform, '### CUDA allocator-cap measurement', '### CUDA 分配器限额测试'), '', | |
| _tr(platform, | |
| f'The saved INT4 checkpoint generated portrait seed 42 at 1024×1024 for 40 steps ' | |
| f'while PyTorch\'s caching allocator was limited to {cap_gib} GiB on this ' | |
| f'{vram_env["gpu"]}. Offload mode: {vram_env["offload"]}: one transformer block or one ' | |
| f'text-encoder leaf on GPU, VAE encode and decode on CPU. ' | |
| f'Allocated peak {vram_row["peak_allocated_bytes"]/2**30:.2f} GiB, ' | |
| f'reserved peak {vram_row["peak_reserved_bytes"]/2**30:.2f} GiB, ' | |
| f'call {vram_row["seconds"]:.2f}s after an excluded warmup. ' | |
| 'These measurements were recorded on the RTX 5090, not on the 8GB laptop described above.', | |
| f'在 {vram_env["gpu"]} 上将 PyTorch 缓存分配器限制为 {cap_gib} GiB 后,' | |
| f'已保存的 INT4 权重完成了 portrait、种子 42、1024×1024、40 步。' | |
| f'卸载方式:{vram_env["offload"]},Transformer 一次一个 block、文本编码器一次一个叶子层放在 GPU,VAE 的编码和解码在 CPU。' | |
| f'已分配峰值 {vram_row["peak_allocated_bytes"]/2**30:.2f} GiB,' | |
| f'保留峰值 {vram_row["peak_reserved_bytes"]/2**30:.2f} GiB,' | |
| f'预热之后的本次调用 {vram_row["seconds"]:.2f} 秒。' | |
| '这些测量值记录于 RTX 5090,并非来自上文提及的 8GB 显存笔记本。'), | |
| '', | |
| f'', | |
| '']) | |
| return {'DETAILS': details, 'SAMPLES': '\n'.join(samples)} | |