<?xml version="1.0" encoding="UTF-8"?>
<rss  xmlns:atom="http://www.w3.org/2005/Atom" 
      xmlns:media="http://search.yahoo.com/mrss/" 
      xmlns:content="http://purl.org/rss/1.0/modules/content/" 
      xmlns:dc="http://purl.org/dc/elements/1.1/" 
      version="2.0">
<channel>
<title>Ritesh Kumar Maurya</title>
<link>https://riteshrm.github.io/notes.html</link>
<atom:link href="https://riteshrm.github.io/notes.xml" rel="self" type="application/rss+xml"/>
<description>Machine learning engineering notes by Ritesh Kumar Maurya.</description>
<generator>quarto-1.8.26</generator>
<lastBuildDate>Tue, 18 Aug 2026 00:00:00 GMT</lastBuildDate>
<item>
  <title>xLAM SFT</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/xlam-sft/</link>
  <description><![CDATA[ 





<ul>
<li>This is a write-up of fine-tuning Qwen2.5-0.5B (base) for tool calling on the xLAM dataset from Salesforce. Along the way I ran into a few subtle bugs — a frozen <code>lm_head</code> that couldn’t learn rare special tokens, tied embeddings breaking silently, and some evaluation bugs that were quietly hiding correct predictions — all documented below. After fixing these, the fine-tuned base model ends up performing on par with, and slightly better than, the zero-shot Instruct model on this task.</li>
</ul>
<section id="motivation" class="level1">
<h1>Motivation</h1>
<p>In case of compute bound, instead of using a large model, can we just fine-tune a small model for domain-specific examples and still get good results? The goal is to fine-tune an SLM for tool calling and check the results. Although current SLMs are already better at tool calling, I still wanted to learn more about SFT and tool calling hands-on.</p>
<section id="why-tool-calling" class="level2">
<h2 class="anchored" data-anchor-id="why-tool-calling">Why tool calling?</h2>
<p>One obvious question might be, why not something else? The reason is that considering the current era of agentic AI, where an LLM needs to call tools to perform some action, the tool accuracy — and alongside that, the arguments passed — becomes more important. It might be possible that due to hallucination, an argument changes from Capital to small caps, where the tool required the text to be capital.</p>
</section>
<section id="why-fine-tune-a-small-model" class="level2">
<h2 class="anchored" data-anchor-id="why-fine-tune-a-small-model">Why fine-tune a small model?</h2>
<p>Since I already mentioned the compute resources, and also, if I can replicate this tool calling with small models, then for larger models it should not be that much more difficult.</p>
</section>
</section>
<section id="model-dataset" class="level1">
<h1>Model &amp; Dataset</h1>
<ul>
<li>The latest SLMs from Qwen are already performing very well on tool calling, so I chose the earlier base model for my experiment, which is Qwen2.5-0.5B.</li>
<li>I have used the xLAM dataset from Salesforce, where a sample looks like:</li>
</ul>
<div class="code-copy-outer-scaffold"><div class="sourceCode" id="cb1" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb1-1">{</span>
<span id="cb1-2">  <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"query"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Find the sum of all the multiples of 3 and 5 between 1 and 1000. Also find the product of the first five prime numbers."</span>,</span>
<span id="cb1-3">  <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"tools"</span>: [</span>
<span id="cb1-4">    {</span>
<span id="cb1-5">      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"name"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"math_toolkit.sum_of_multiples"</span>,</span>
<span id="cb1-6">      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"description"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Find the sum of all multiples of specified numbers within a specified range."</span>,</span>
<span id="cb1-7">      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"parameters"</span>: {</span>
<span id="cb1-8">        <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"lower_limit"</span>: {</span>
<span id="cb1-9">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"type"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"int"</span>,</span>
<span id="cb1-10">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"description"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"The start of the range (inclusive)."</span>,</span>
<span id="cb1-11">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"required"</span>: <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span></span>
<span id="cb1-12">        },</span>
<span id="cb1-13">        <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"upper_limit"</span>: {</span>
<span id="cb1-14">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"type"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"int"</span>,</span>
<span id="cb1-15">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"description"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"The end of the range (inclusive)."</span>,</span>
<span id="cb1-16">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"required"</span>: <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span></span>
<span id="cb1-17">        },</span>
<span id="cb1-18">        <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"multiples"</span>: {</span>
<span id="cb1-19">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"type"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"list"</span>,</span>
<span id="cb1-20">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"description"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"The numbers to find multiples of."</span>,</span>
<span id="cb1-21">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"required"</span>: <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span></span>
<span id="cb1-22">        }</span>
<span id="cb1-23">      }</span>
<span id="cb1-24">    },</span>
<span id="cb1-25">    {</span>
<span id="cb1-26">      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"name"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"math_toolkit.product_of_primes"</span>,</span>
<span id="cb1-27">      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"description"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Find the product of the first n prime numbers."</span>,</span>
<span id="cb1-28">      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"parameters"</span>: {</span>
<span id="cb1-29">        <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"count"</span>: {</span>
<span id="cb1-30">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"type"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"int"</span>,</span>
<span id="cb1-31">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"description"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"The number of prime numbers to multiply together."</span>,</span>
<span id="cb1-32">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"required"</span>: <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span></span>
<span id="cb1-33">        }</span>
<span id="cb1-34">      }</span>
<span id="cb1-35">    }</span>
<span id="cb1-36">  ],</span>
<span id="cb1-37">  <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"answers"</span>: [</span>
<span id="cb1-38">    {</span>
<span id="cb1-39">      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"name"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"math_toolkit.sum_of_multiples"</span>,</span>
<span id="cb1-40">      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"arguments"</span>: {</span>
<span id="cb1-41">        <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"lower_limit"</span>: <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>,</span>
<span id="cb1-42">        <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"upper_limit"</span>: <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1000</span>,</span>
<span id="cb1-43">        <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"multiples"</span>: [<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">5</span>]</span>
<span id="cb1-44">      }</span>
<span id="cb1-45">    },</span>
<span id="cb1-46">    {</span>
<span id="cb1-47">      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"name"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"math_toolkit.product_of_primes"</span>,</span>
<span id="cb1-48">      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"arguments"</span>: {</span>
<span id="cb1-49">        <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"count"</span>: <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">5</span></span>
<span id="cb1-50">      }</span>
<span id="cb1-51">    }</span>
<span id="cb1-52">  ]</span>
<span id="cb1-53">}</span></code></pre></div></div>
<ul>
<li>I have used <code>True</code> instead of <code>true</code>, since the sample is shown as a Python dict here rather than raw JSON.</li>
<li>Each JSON object specifies:
<ul>
<li><strong>query</strong> — the query with the params possibly needed for the tools</li>
<li><strong>tools</strong> — the available tools which can be called, where each tool has a description and specifies its arguments; each argument has a description, the type of arg it takes, and whether it’s required</li>
<li><strong>answers</strong> — a list of tools and their corresponding args (key-value pairs) which need to be passed to the tool</li>
</ul></li>
</ul>
</section>
<section id="preparing-the-dataset" class="level1">
<h1>Preparing the Dataset</h1>
<ul>
<li>Instead of using all 60k samples, I took only 2,500 samples, where I used 2000 as train, 100 as validation, and 400 as test samples.</li>
<li>Given the query, tools, and answers, I needed to apply a chat template to convert them into the required format.</li>
<li>For that purpose, I used the chat template of Qwen2.5-0.5B and defined two functions — one for train/validation, and another for test.</li>
</ul>
<div id="943f6586" class="cell" data-execution_count="1">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb2" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb2-1"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> generate_train_val_sample(sample):</span>
<span id="cb2-2">  messages <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [</span>
<span id="cb2-3">      {</span>
<span id="cb2-4">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"role"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"user"</span>,</span>
<span id="cb2-5">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"content"</span>: sample[<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"query"</span>]</span>
<span id="cb2-6">      },</span>
<span id="cb2-7">      {</span>
<span id="cb2-8">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"role"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"assistant"</span>,</span>
<span id="cb2-9">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"tool_calls"</span>: [</span>
<span id="cb2-10">              {</span>
<span id="cb2-11">                  <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"function"</span>: {</span>
<span id="cb2-12">                      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"name"</span>: answer[<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"name"</span>],</span>
<span id="cb2-13">                      <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"arguments"</span>: answer[<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"arguments"</span>]</span>
<span id="cb2-14">                  }</span>
<span id="cb2-15">              }</span>
<span id="cb2-16">              <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> answer <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> json.loads(sample[<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"answers"</span>])</span>
<span id="cb2-17">          ]</span>
<span id="cb2-18">      }</span>
<span id="cb2-19">  ]</span>
<span id="cb2-20"></span>
<span id="cb2-21">  tools <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> json.loads(sample[<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"tools"</span>])</span>
<span id="cb2-22">  text <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> tokenizer.apply_chat_template(</span>
<span id="cb2-23">        messages,</span>
<span id="cb2-24">        tools<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>tools,</span>
<span id="cb2-25">        tokenize<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>,</span>
<span id="cb2-26">        add_generation_prompt<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>,</span>
<span id="cb2-27">    )</span>
<span id="cb2-28"></span>
<span id="cb2-29">  <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span>  {<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"text"</span>: text}</span></code></pre></div></div>
</div>
<div id="15e16fa3" class="cell" data-execution_count="2">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb3" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb3-1"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> generate_test_sample(sample):</span>
<span id="cb3-2">  messages <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [</span>
<span id="cb3-3">      {</span>
<span id="cb3-4">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"role"</span>: <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"user"</span>,</span>
<span id="cb3-5">          <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"content"</span>: sample[<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"query"</span>]</span>
<span id="cb3-6">      }</span>
<span id="cb3-7">  ]</span>
<span id="cb3-8"></span>
<span id="cb3-9">  tools <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> json.loads(sample[<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"tools"</span>])</span>
<span id="cb3-10">  text <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> tokenizer.apply_chat_template(</span>
<span id="cb3-11">        messages,</span>
<span id="cb3-12">        tools<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>tools,</span>
<span id="cb3-13">        tokenize<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>,</span>
<span id="cb3-14">        add_generation_prompt<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span>,</span>
<span id="cb3-15">    )</span>
<span id="cb3-16"></span>
<span id="cb3-17">  <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span>  {<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"text"</span>: text}</span></code></pre></div></div>
</div>
<ul>
<li><p>As can be seen from the functions above, we pass <code>answers</code> in the case of train and validation and set <code>add_generation_prompt</code> to <code>False</code>, since we are not generating — we are comparing against the already-known text.</p></li>
<li><p>For test, we don’t pass <code>answers</code>, and we set <code>add_generation_prompt</code> to <code>True</code>.</p></li>
<li><p>Using these two functions, we can convert any sample into the required format.</p></li>
</ul>
<p><strong>Converted train/validation sample</strong></p>
<pre class="text"><code>&lt;|im_start|&gt;system
You are a helpful assistant.

# Tools

You may call one or more functions to assist with the user query.

You are provided with function signatures within &lt;tools&gt;&lt;/tools&gt; XML tags:
&lt;tools&gt;
{"name": "get_order", "description": "Fetches the order information for a given order ID using the Toolbench RapidAPI.", "parameters": {"is_id": {"description": "The ID of the order to be fetched.", "type": "str", "default": ""}}}
&lt;/tools&gt;

For each function call, return a json object with function name and arguments within &lt;tool_call&gt;&lt;/tool_call&gt; XML tags:
&lt;tool_call&gt;
{"name": &lt;function-name&gt;, "arguments": &lt;args-json-object&gt;}
&lt;/tool_call&gt;&lt;|im_end|&gt;
&lt;|im_start|&gt;user
Retrieve the order status for \'ORD11223\' and \'ORD44556\'.&lt;|im_end|&gt;
&lt;|im_start|&gt;assistant
&lt;tool_call&gt;
{"name": "get_order", "arguments": {"is_id": "ORD11223"}}
&lt;/tool_call&gt;
&lt;tool_call&gt;
{"name": "get_order", "arguments": {"is_id": "ORD44556"}}
&lt;/tool_call&gt;&lt;|im_end|&gt;'</code></pre>
<p><strong>Converted test sample</strong></p>
<pre class="text"><code>&lt;|im_start|&gt;system
You are a helpful assistant.

# Tools

You may call one or more functions to assist with the user query.

You are provided with function signatures within &lt;tools&gt;&lt;/tools&gt; XML tags:
&lt;tools&gt;
{"name": "get_order", "description": "Fetches the order information for a given order ID using the Toolbench RapidAPI.", "parameters": {"is_id": {"description": "The ID of the order to be fetched.", "type": "str", "default": ""}}}
&lt;/tools&gt;

For each function call, return a json object with function name and arguments within &lt;tool_call&gt;&lt;/tool_call&gt; XML tags:
&lt;tool_call&gt;
{"name": &lt;function-name&gt;, "arguments": &lt;args-json-object&gt;}
&lt;/tool_call&gt;&lt;|im_end|&gt;
&lt;|im_start|&gt;user
Retrieve the order status for \'ORD11223\' and \'ORD44556\'.&lt;|im_end|&gt;
&lt;|im_start|&gt;assistant</code></pre>
<ul>
<li>I’ve used the same example above to show how it looks in both train/validation and test form.</li>
<li>As we can see, the text contains all the required pieces — system prompt, user query, and available tools — and depending on the type of sample, it either includes the assistant’s response and ends with the <code>&lt;|im_end|&gt;</code> token, or it ends right at <code>&lt;|im_start|&gt;assistant</code>, triggering the model to generate the response.</li>
</ul>
</section>
<section id="sft-setup" class="level1">
<h1>SFT Setup</h1>
<ul>
<li>I used PEFT and TRL for doing supervised fine-tuning, and didn’t use Unsloth because Unsloth requires some of the latest GPUs, and my current laptop (RTX 1050, 3GB) doesn’t have that.</li>
<li>I had the option of using Colab, but at the same time, I wanted to check the internal working of the functions I was importing, so instead I switched to my local setup.</li>
</ul>
<section id="phase-1" class="level2">
<h2 class="anchored" data-anchor-id="phase-1">Phase 1</h2>
<ul>
<li>In case of the PEFT configuration:
<ul>
<li>I used rank 16 and <code>lora_alpha</code> 32 [following the HuggingFace SFT article]</li>
<li>Target modules were <code>q_proj</code>, <code>k_proj</code>, <code>v_proj</code>, <code>o_proj</code>, <code>gate_proj</code>, <code>up_proj</code>, <code>down_proj</code></li>
</ul></li>
<li>I fine-tuned and checked the results.</li>
<li>Some weird tokens were coming in place of <code>&lt;tool_call&gt;</code> and <code>&lt;/tool_call&gt;</code>.</li>
<li>Eventually I found out that, since I was fine-tuning a base model, the embedding/<code>lm_head</code> doesn’t know much about the <code>tool_call</code> token. Also, <code>embed_tokens</code> and <code>lm_head</code> are tied in the base model, so I needed to account for that too — otherwise the two matrices would end up with different values instead of staying tied.</li>
</ul>
</section>
<section id="phase-2" class="level2">
<h2 class="anchored" data-anchor-id="phase-2">Phase 2</h2>
<ul>
<li>I trained <code>embed_tokens</code> instead of keeping it frozen, while making sure there wouldn’t end up being two separate matrices instead of one, by passing <code>ensure_weight_tying=True</code>.
<ul>
<li><code>modules_to_save=["lm_head", "embed_tokens"]</code></li>
<li><code>ensure_weight_tying=True</code></li>
</ul></li>
<li>Below is the PEFT config I used finally:</li>
</ul>
<pre class="text"><code>peft_config = LoraConfig(
    r=16,
    lora_alpha=32,
    task_type=TaskType.CAUSAL_LM,
    target_modules=["q_proj", "k_proj", "v_proj", "o_proj", "gate_proj", "up_proj", "down_proj"],
    modules_to_save=["lm_head", "embed_tokens"],
    ensure_weight_tying=True,
)</code></pre>
<ul>
<li>Below is the <code>SFTConfig</code> I used:</li>
</ul>
<pre class="text"><code>training_args = SFTConfig(
    # Training schedule / optimization
    per_device_train_batch_size = BATCH_SIZE,      # Batch size per GPU
    gradient_accumulation_steps = 4,      # Effective batch size = 1 * 4 = 4
    warmup_steps = WARMUP_STEPS,
    max_steps=MAX_STEPS,
    learning_rate = 2e-4,                 # Learning rate for the optimizer
    optim = "paged_adamw_8bit",           # Optimizer

    # Logging / reporting
    eval_strategy="steps",
    eval_steps=EVAL_STEPS,
    save_strategy="steps",
    save_steps=SAVE_STEPS,
    save_total_limit=2,
    load_best_model_at_end=True,
    metric_for_best_model="eval_loss",
    greater_is_better=False,
    logging_steps=1,                      # Log training metrics every N steps
    report_to="trackio",                  # Experiment tracking tool
    run_name="testing",
    output_dir=OUTPUT_DIR,                # Where to save model checkpoints and logs

    max_length=1024,                      # Maximum input sequence length
    activation_offloading=True,           # Offload activations to CPU to reduce GPU memory usage
)</code></pre>
<ul>
<li>Specifically, batch size is 1 with gradient accumulation of 4, and learning rate is 2e-4.</li>
<li>Sequence length was 1024, since I didn’t need to generate a whole paragraph, and max train steps were only 500 — I think if I train it for longer, the results would likely get better.</li>
<li>Training setup: I used CUDA-enabled PyTorch with some restrictions, like not being able to use <code>torch.compile</code> due to the older GPU. I used Trackio to track training and validation logs.</li>
</ul>
</section>
<section id="training-logs" class="level2">
<h2 class="anchored" data-anchor-id="training-logs">Training Logs</h2>
<div style="display: flex; justify-content: center; gap: 20px;">
<figure style="text-align: center; width: 48%;" class="figure">
<img src="https://riteshrm.github.io/posts/xlam-sft/train_loss.png" style="width: 100%;" class="figure-img">
<figcaption>
Train Loss
</figcaption>
</figure>
<figure style="text-align: center; width: 48%;" class="figure">
<img src="https://riteshrm.github.io/posts/xlam-sft/train_entropy.png" style="width: 100%;" class="figure-img">
<figcaption>
Train Entropy
</figcaption>
</figure>
</div>
<div style="display: flex; justify-content: center; gap: 20px;">
<figure style="text-align: center; width: 48%;" class="figure">
<img src="https://riteshrm.github.io/posts/xlam-sft/eval_loss.png" style="width: 100%;" class="figure-img">
<figcaption>
Evaluation Loss
</figcaption>
</figure>
<figure style="text-align: center; width: 48%;" class="figure">
<img src="https://riteshrm.github.io/posts/xlam-sft/eval_entropy.png" style="width: 100%;" class="figure-img">
<figcaption>
Evaluation Entropy
</figcaption>
</figure>
</div>
</section>
</section>
<section id="evaluation" class="level1">
<h1>Evaluation</h1>
<ul>
<li>first i checked whether the predicted answers have all the available tools as present in ground truth and then checked for the arguments present and the values passed against those arguments</li>
<li>compared the result of finetuned base model with instruct version of qwen-2.5-0.5B</li>
</ul>
</section>
<section id="results" class="level1">
<h1>Results</h1>
<p><strong>Before fine-tuning (base model)</strong></p>
<pre class="text"><code>User Query: I need an advanced chart for 'BINANCE:ETHUSDT' with MACD and RSI indicators, in light theme, and a 4h interval. Also, provide a list of stocks that are overbought according to RSI on page 3.
Actual Output: [{"name": "advanced_chart", "arguments": {"symbol": "BINANCE:ETHUSDT", "studies": "MACD,RSI", "theme": "light", "interval": "4h"}}, {"name": "rsi_overbought", "arguments": {"page": 3}}]
Predicted Output: To fetch the advanced chart for 'BINANCE:ETHUSDT' with MACD and RSI indicators, in light theme, and a 4h interval, you can use the following code:

{
    "name": "advanced_chart",
    "arguments": {
        "symbol": "BINANCE:ETHUSDT",
        "studies": ["MACD", "RSI"],
        "format": "png",
        "theme": "light",
        "interval": "4h",
        "width": 800,
        "height": 600,
        "timezone": "Etc/UTC"
    }
}

This code will fetch the advanced chart for 'BINANCE:ETHUSDT' with MACD and RSI indicators, in light theme, and a 4h interval. The arguments include the symbol, studies, format, theme, interval, width, height, and timezone.

To fetch a list of stocks that are overbought according to RSI on page 3, you can use the following code:

{
    "name": "rsi_overbought",
    "arguments": {
        "page": 3,
        "studies": ["RSI"],
        "format": "png",
        "theme": "light",
        "interval": "4h",
        "width": 800,
        "height": 600,
        "timezone": "Etc/UTC"
    }
}

This code will fetch a list of stocks that are overbought according to RSI on page 3, with MACD and RSI indicators, in light theme, and a 4h interval. The arguments include the page number, studies, format, theme, interval, width, height, and timezone.</code></pre>
<p>The base model, before fine-tuning, doesn’t call tools at all — it responds conversationally and hallucinates extra arguments (<code>format</code>, <code>width</code>, <code>height</code>, <code>timezone</code>) that were never part of the tool’s actual schema.</p>
<p><strong>After fine-tuning</strong></p>
<pre class="text"><code>User Query: I need an advanced chart for 'BINANCE:ETHUSDT' with MACD and RSI indicators, in light theme, and a 4h interval. Also, provide a list of stocks that are overbought according to RSI on page 3.
Actual Output: [{"name": "advanced_chart", "arguments": {"symbol": "BINANCE:ETHUSDT", "studies": "MACD,RSI", "theme": "light", "interval": "4h"}}, {"name": "rsi_overbought", "arguments": {"page": 3}}]
Predicted Output: &lt;tool_call&gt;
{"name": "advanced_chart", "arguments": {"symbol": "BINANCE:ETHUSDT", "studies": "MACD,RSI", "theme": "light", "interval": "4h"}}
&lt;/tool_call&gt;
&lt;tool_call&gt;
{"name": "rsi_overbought", "arguments": {"page": 3}}
&lt;/tool_call&gt;</code></pre>
<p>After fine-tuning, the model correctly emits both tool calls in the expected <code>&lt;tool_call&gt;</code> format, with arguments matching the ground truth exactly.</p>
<section id="evaluated-on-400-held-out-test-samples" class="level2">
<h2 class="anchored" data-anchor-id="evaluated-on-400-held-out-test-samples">Evaluated on 400 held-out test samples</h2>
<table class="caption-top table">
<thead>
<tr class="header">
<th>Metric</th>
<th style="text-align: center;">Base (LoRA)</th>
<th style="text-align: center;">Instruct (zero-shot)</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td>Valid JSON</td>
<td style="text-align: center;">98.75%</td>
<td style="text-align: center;">96.75%</td>
</tr>
<tr class="even">
<td>Exact Match</td>
<td style="text-align: center;">58.75%</td>
<td style="text-align: center;">59.25%</td>
</tr>
<tr class="odd">
<td>Tool Accuracy</td>
<td style="text-align: center;">93.89%</td>
<td style="text-align: center;">92.45%</td>
</tr>
<tr class="even">
<td>Argument Accuracy</td>
<td style="text-align: center;">81.58%</td>
<td style="text-align: center;">80.64%</td>
</tr>
</tbody>
</table>
</section>
</section>
<section id="what-i-learned" class="level1">
<h1>What I Learned</h1>
<ul>
<li>For SLMs, the embedding and <code>lm_head</code> are generally kept tied, to reduce the parameter count.</li>
<li>In this case, the tokenizer’s vocab size was lesser than the number of tokens the embedding module could actually represent — this extra headroom becomes useful if new tokens need to be added during fine-tuning.</li>
<li>When adding extra tokens, the embedding and <code>lm_head</code> also need to be trained — otherwise the model produces weird/garbage tokens as output.</li>
</ul>
</section>
<section id="code" class="level1">
<h1>Code</h1>
<p>Full training and evaluation code: https://github.com/riteshrm/qwen2.5-tool-calling-lora</p>


</section>

 ]]></description>
  <category>Generative AI</category>
  <guid>https://riteshrm.github.io/posts/xlam-sft/</guid>
  <pubDate>Tue, 18 Aug 2026 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/xlam-sft/thumbnail.png" medium="image" type="image/png" height="123" width="144"/>
</item>
<item>
  <title>Flow Matching</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/flow-matching/</link>
  <description><![CDATA[ 





<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Tip</span>References
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>This is mostly based on:
<ol type="1">
<li><a href="https://www.youtube.com/watch?v=agN3AlfGFrk">Stanford CME296 Diffusion &amp; Large Vision Models | Spring 2026 | Lecture 3 - Flow matching</a></li>
<li><a href="https://www.youtube.com/watch?v=7cMzfkWFWhI">Flow Matching | Explanation + PyTorch Implementation</a></li>
<li><a href="https://arxiv.org/abs/2210.02747">Flow Matching for Generative Modeling</a></li>
</ol></li>
</ul>
</div>
</div>
<hr>
<ul>
<li>Minimal PyTorch implementation accompanying these notes:
<ul>
<li><a href="https://github.com/riteshrm/nanoFM">nanoFM GitHub Repo</a></li>
</ul></li>
</ul>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Note</span>Reading map
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>Motivation</li>
<li>Flow Models</li>
<li>Earlier attempts to learn the velocity</li>
<li>Flow Matching</li>
<li>Implementation</li>
</ul>
</div>
</div>
<hr>
<section id="motivation" class="level2">
<h2 class="anchored" data-anchor-id="motivation">Motivation</h2>
<section id="objective-and-solution" class="level3">
<h3 class="anchored" data-anchor-id="objective-and-solution">Objective and solution</h3>
<ul>
<li><strong>Objective:</strong> Given a complex data distribution how can we go from simple distribution to complex data distribution.</li>
<li><strong>Solution:</strong> Use vector field, which will guide to go towards target distribution <img src="https://latex.codecogs.com/png.latex?P_1%20=%20P_%7Bdata%7D"> from initial distribution <img src="https://latex.codecogs.com/png.latex?P_0%20=%20N(0,%20I)"></li>
</ul>
</section>
<section id="some-terminology" class="level3">
<h3 class="anchored" data-anchor-id="some-terminology">Some terminology</h3>
<ul>
<li>Trajectory <img src="https://latex.codecogs.com/png.latex?x_t">: path taken by the observation for time t <img src="https://latex.codecogs.com/png.latex?%5Cepsilon"> [0, 1]
<ul>
<li>For example:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x_0">: from <img src="https://latex.codecogs.com/png.latex?P_0"> to <img src="https://latex.codecogs.com/png.latex?P_1"></li>
<li><img src="https://latex.codecogs.com/png.latex?x_t">: from <img src="https://latex.codecogs.com/png.latex?P_0"> to <img src="https://latex.codecogs.com/png.latex?P_t"></li>
</ul></li>
</ul></li>
<li>Flow <img src="https://latex.codecogs.com/png.latex?%5Cpsi(x_0)">: Collections of trajectories <img src="https://latex.codecogs.com/png.latex?x_t"> which start from different <img src="https://latex.codecogs.com/png.latex?x_0"></li>
<li>Probability path <img src="https://latex.codecogs.com/png.latex?p_t(x)">: Probability distribution of <img src="https://latex.codecogs.com/png.latex?x_t"> at time t.</li>
<li>Vector field <img src="https://latex.codecogs.com/png.latex?u_t(x)">: where to move(direction, speed) at time t and location x</li>
</ul>
</section>
<section id="velocity-vs-score" class="level3">
<h3 class="anchored" data-anchor-id="velocity-vs-score">Velocity vs Score</h3>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Note
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>Velocity is like giving instructions to self-driving car at point x and time t whereas score is like compass in the car, which tells where the high probability regions are.</li>
</ul>
</div>
</div>
</section>
<section id="perspective-of-a-single-sample-with-ode" class="level3">
<h3 class="anchored" data-anchor-id="perspective-of-a-single-sample-with-ode">Perspective of a single sample with ODE</h3>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?dx%20=%20u_t(x)dt"></li>
<li>where:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?dx"> is change in sample position</li>
<li><img src="https://latex.codecogs.com/png.latex?u_t(x)"> is velocity field at location x and time t</li>
<li><img src="https://latex.codecogs.com/png.latex?dt"> is change in time</li>
</ul></li>
<li>Trajectory starting from <img src="https://latex.codecogs.com/png.latex?x_0"> (<img src="https://latex.codecogs.com/png.latex?u_t(x_0)">) is unique if velocity <img src="https://latex.codecogs.com/png.latex?u_t(x)"> is lipschitz continuous</li>
</ul>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Tip</span>Lipschitz Continuity
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>A function f is lipschitz continuous, when we have some constant M, (x, y) from space of interest such that:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%7C%7Cf(x)%20-%20f(y)%7C%7C%20%5Cleq%20M.%7C%7Cx%20-%20y%7C%7C"></li>
<li>which means f needs to be continuous but not in a very dramatic way</li>
</ul></li>
</ul>
</div>
</div>
</section>
<section id="perspective-of-a-distribution-via-mass-conservation" class="level3">
<h3 class="anchored" data-anchor-id="perspective-of-a-distribution-via-mass-conservation">Perspective of a distribution via “Mass Conservation”</h3>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/flow-matching/volume.png" style="width:25%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Tip
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7B%5Cdelta%20p_t%7D%7B%5Cdelta%20t%7D(x)%20=%20Inflow%20of%20density%20-%20Outflow%20of%20density"></li>
<li>Where:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7B%5Cdelta%20p_t%7D%7B%5Cdelta%20t%7D(x)"> is temporal evolution of density at time t at a particular location</li>
</ul></li>
</ul>
</div>
</div>
</section>
<section id="intuition-behind-divergence-in-1d" class="level3">
<h3 class="anchored" data-anchor-id="intuition-behind-divergence-in-1d">Intuition behind divergence in 1D</h3>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Note
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>divergence <img src="https://latex.codecogs.com/png.latex?%5Cgeq"> 0 (things are coming out more than coming in)
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7B%5Cdelta%20f%7D%7B%5Cdelta%20x%7D%20%5Cgeq%200"></li>
</ul></li>
<li>divergence <img src="https://latex.codecogs.com/png.latex?%5Cleq"> 0 (things are coming in more than going out)
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7B%5Cdelta%20f%7D%7B%5Cdelta%20x%7D%20%5Cleq%200"></li>
</ul></li>
<li>Generalization for n dimensions:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?div(f)%20=%20%5Ctriangledown%20.%20f%20=%20%5Csum_%7Bi=1%7D%5E%7Bn%7D%5Cfrac%7B%5Cdelta%20f%7D%7B%5Cdelta%20x_i%7D"></li>
</ul></li>
<li>Which function should we select as f?
<ul>
<li>Suppose we have:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?u_t(x_1)%20=%20u_t(x_2)"></li>
<li><img src="https://latex.codecogs.com/png.latex?p_t(x_1)%20%3C%20p_t(x_2)"></li>
</ul></li>
<li>and we want:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%7C%7Cf(x_1)%7C%7C%20%3C%20%7C%7Cf(x_2)%7C%7C"></li>
</ul></li>
<li>One option would be Vector field <img src="https://latex.codecogs.com/png.latex?u_t(x)">?
<ul>
<li>But we want to transfer from high density region more as compared to lower density region which is not possible using vector fields since they have only direction and magnitude not probability distribution</li>
</ul></li>
<li>So probability flux
<ul>
<li><img src="https://latex.codecogs.com/png.latex?(p_t%20u_t)(x)"></li>
<li><img src="https://latex.codecogs.com/png.latex?p_t"> is probability density</li>
<li><img src="https://latex.codecogs.com/png.latex?u_t"> is velocity</li>
</ul></li>
<li>which finally gives
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7B%5Cdelta%20p_t%7D%7B%5Cdelta%20t%7D(x)%20=%20-%5Ctriangledown(p_t%20u_t)(x)"></li>
</ul></li>
</ul></li>
</ul>
</div>
</div>
</section>
<section id="two-perspectives-involving-the-velocity" class="level3">
<h3 class="anchored" data-anchor-id="two-perspectives-involving-the-velocity">Two perspectives involving the velocity</h3>
<ul>
<li>Single Sample(Micro level)
<ul>
<li><figure style="text-align: left;" class="figure">
<img src="https://riteshrm.github.io/posts/flow-matching/single_sample.png" style="width:20%" class="figure-img">
<figcaption>
</figcaption>
</figure></li>
<li><img src="https://latex.codecogs.com/png.latex?x_0%20%5Csim%20p_0"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7Bdx_t%7D%7Bdt%7D%20=%20u_t(x)"></li>
</ul></li>
<li>Distribution (Macro level)
<ul>
<li><figure style="text-align: left;" class="figure">
<img src="https://riteshrm.github.io/posts/flow-matching/distribution.png" style="width:20%" class="figure-img">
<figcaption>
</figcaption>
</figure></li>
<li><img src="https://latex.codecogs.com/png.latex?x_t%20%5Csim%20p_t"></li>
</ul></li>
<li>Vector field <img src="https://latex.codecogs.com/png.latex?u_t"> generates the probability path <img src="https://latex.codecogs.com/png.latex?p_t(x)"></li>
<li>We want to go from <img src="https://latex.codecogs.com/png.latex?p_0"> to <img src="https://latex.codecogs.com/png.latex?p_1"> and for that we will need vector fields which will actually allows to do the mapping</li>
</ul>
</section>
</section>
<section id="flow-models" class="level2">
<h2 class="anchored" data-anchor-id="flow-models">Flow Models</h2>
<section id="goal-and-strategy" class="level3">
<h3 class="anchored" data-anchor-id="goal-and-strategy">Goal and strategy</h3>
<ul>
<li>Goal: Map <img src="https://latex.codecogs.com/png.latex?x_0%20%5Csim%20p_0%20%5Crightarrow%20x_1%20%5Csim%20p_1"></li>
<li>Strategy:
<ul>
<li>Training: Estimate <img src="https://latex.codecogs.com/png.latex?u_t(x)"> for all time t and all locations x via <img src="https://latex.codecogs.com/png.latex?u%5E%7B%5Ctheta%7D_t(x)"></li>
<li>Inference: Sample from initial distribution and solve numerically the ODE using the learned vector field <img src="https://latex.codecogs.com/png.latex?u%5E%7B%5Ctheta%7D_t(x)">
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Chat%7Bx_1%7D%20=%20x_0%20+%20%5Cint_%7B0%7D%5E%7B1%7Du%5E%7B%5Ctheta%7D_t(x)dt"></li>
</ul></li>
</ul></li>
</ul>
</section>
</section>
<section id="earlier-attempts-to-learn-the-velocity" class="level2">
<h2 class="anchored" data-anchor-id="earlier-attempts-to-learn-the-velocity">Earlier attempts to learn the velocity</h2>
<section id="why-this-was-harder" class="level3">
<h3 class="anchored" data-anchor-id="why-this-was-harder">Why this was harder</h3>
<ul>
<li>Goal: Learn the vector field <img src="https://latex.codecogs.com/png.latex?u_t(x)"> via maximum likelihood</li>
<li>Idea: Transform continuity equation to:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7Bd%7D%7Bdt%7D%20log%20p_t(x)%20=%20-%20%5Ctriangledown%20.%20u_t(x)"></li>
</ul></li>
<li>Then simulate ODE at training time to maximize likelihood:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?logp%5E%5Ctheta_1(x_1)%20=%20logp%5E%5Ctheta_0(x_0)%20+%20%5Cint_%7B0%7D%5E%7B1%7D%20-%20%5Ctriangledown%20.u%5E%7B%5Ctheta%7D_t(x)dt"></li>
</ul></li>
<li>Limitation: Training is slow and expensive because of the integral, that’s why flow matching was introduced</li>
</ul>
</section>
</section>
<section id="flow-matching" class="level2">
<h2 class="anchored" data-anchor-id="flow-matching">Flow Matching</h2>
<section id="core-idea" class="level3">
<h3 class="anchored" data-anchor-id="core-idea">Core idea</h3>
<ul>
<li>Goal: Estimate the vector field with <img src="https://latex.codecogs.com/png.latex?u%5E%5Ctheta_t(x)"> instead of maximizing the likelihood
<ul>
<li><img src="https://latex.codecogs.com/png.latex?L_%7BFM%7D%20=%20%5Cmathbb%7BE%7D_%7Bt,%20x%7D%5B%7C%7Cu%5E%5Ctheta_t(x)%20-%20u_t(x)%7C%7C%5E2%5D"></li>
</ul></li>
<li>But we don’t have access to <img src="https://latex.codecogs.com/png.latex?u_t(x)"></li>
</ul>
</section>
<section id="why-conditional-paths-help" class="level3">
<h3 class="anchored" data-anchor-id="why-conditional-paths-help">Why conditional paths help</h3>
<ul>
<li><p>How do we get this vector field, which will allow us to go from <img src="https://latex.codecogs.com/png.latex?p_0"> to <img src="https://latex.codecogs.com/png.latex?p_1"></p></li>
<li><p>Let’s assume <img src="https://latex.codecogs.com/png.latex?p_%7Bdata%7D"> is composed of points from training data, so instead of finding out vector field for initial distribution to final distribution, we make it easier and look for vector field from initial distribution to some point in data distribution i.e.&nbsp;Initial Distribution <img src="https://latex.codecogs.com/png.latex?%5Crightarrow"> Dirac Distribution</p></li>
</ul>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Tip</span>Dirac Distribution
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>Something which is deterministic unlike general distributions</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cdelta_%7Bx_1%7D(x)%20=%200%20%5C:%20if%20%5C:%20x%20%5Cneq%20x_1"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cdelta_%7Bx_1%7D(x)%20=%20+%20%5Cinfty%20%5C:%20if%20x%20=%20x_1"></li>
</ul>
</div>
</div>
</section>
<section id="conditional-probability-path" class="level3">
<h3 class="anchored" data-anchor-id="conditional-probability-path">Conditional probability path</h3>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?p_t(x%20%5Cmid%20x_1)%20=%20N(tx_1,%20(1-t)%5E2I)">
<figure style="text-align: left;" class="figure">
<img src="https://riteshrm.github.io/posts/flow-matching/cpp.png" style="width:40%" class="figure-img">
<figcaption>
</figcaption>
</figure></li>
</ul>
</section>
<section id="conditional-vector-path" class="level3">
<h3 class="anchored" data-anchor-id="conditional-vector-path">Conditional vector path</h3>
<ul>
<li>One of the vector fields generating probability path</li>
<li><img src="https://latex.codecogs.com/png.latex?u_t(x%20%5Cmid%20x_1)%20=%20%5Cfrac%7Bx_1%20-%20x%7D%7B1-t%7D">
<figure style="text-align: left;" class="figure">
<img src="https://riteshrm.github.io/posts/flow-matching/cvp.png" style="width:40%" class="figure-img">
<figcaption>
</figcaption>
</figure></li>
</ul>
</section>
<section id="conditional-vector-fields-and-probability-path" class="level3">
<h3 class="anchored" data-anchor-id="conditional-vector-fields-and-probability-path">Conditional vector fields and probability path</h3>
<ul>
<li>Conditional Vector Fields [<img src="https://latex.codecogs.com/png.latex?u_t(.%20%5Cmid%20x_1)">] generates Conditional Probability Path [<img src="https://latex.codecogs.com/png.latex?p_t(.%20%5Cmid%20x_1)">]</li>
<li>Using continuity equation, we can derive:
<ul>
<li>if <img src="https://latex.codecogs.com/png.latex?x_0%20%5Csim%20p_0(.%20%5Cmid%20x_1)"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7Bdx_t%7D%7Bdt%7D%20=%20u_t(x_t%20%5Cmid%20x_1)"> then</li>
<li><img src="https://latex.codecogs.com/png.latex?x_t%20%5Csim%20p_t(.%20%5Cmid%20x_1)"></li>
<li>Since <img src="https://latex.codecogs.com/png.latex?p_t(.%20%5Cmid%20x_1)%20=%20N(tx_1,%20(1-t)%5E2I)"></li>
<li><img src="https://latex.codecogs.com/png.latex?x_t%20=%20tx_1%20+%20(1-t)x_0"> where <img src="https://latex.codecogs.com/png.latex?x_0%20%5Csim%20N(0,%20I)"></li>
<li><img src="https://latex.codecogs.com/png.latex?u_t(x_t%20%5Cmid%20x_1)%20=%20%5Cfrac%7Bx_1-%5Btx_1%20+%20(1-t)x_0%5D%7D%7B1-t%7D%20=%20x_1%20-%20x_0"></li>
</ul></li>
</ul>
</section>
<section id="marginal-probability-path" class="level3">
<h3 class="anchored" data-anchor-id="marginal-probability-path">Marginal probability path</h3>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Tip
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li><img src="https://latex.codecogs.com/png.latex?p_t"> is an aggregation of <img src="https://latex.codecogs.com/png.latex?p_t(.%20%5Cmid%20x%5E%7B(i)%7D_1)">
<figure style="text-align: left;" class="figure">
<img src="https://riteshrm.github.io/posts/flow-matching/mvp.png" style="width:40%" class="figure-img">
<figcaption>
</figcaption>
</figure></li>
<li><img src="https://latex.codecogs.com/png.latex?p_t(x)%20=%20%5Cint%20p_t(x%20%5Cmid%20x_1)p_%7Bdata%7D(x_1)dx_1"></li>
<li>From above definition, we can say that:
<ul>
<li>At t=0, <img src="https://latex.codecogs.com/png.latex?p_%7Bt=0%7D%20=%20p_0"> where <img src="https://latex.codecogs.com/png.latex?p_%7Bt=0%7D"> is marginal probability path for t=0 and <img src="https://latex.codecogs.com/png.latex?p_0"> is initial probability distribution</li>
<li>At t=1, <img src="https://latex.codecogs.com/png.latex?p_%7Bt=1%7D%20=%20p_1"> where <img src="https://latex.codecogs.com/png.latex?p_%7Bt=1%7D"> is marginal probability path for t=1 and <img src="https://latex.codecogs.com/png.latex?p_1"> is target probability distribution</li>
</ul></li>
</ul>
</div>
</div>
</section>
<section id="marginal-vector-field" class="level3">
<h3 class="anchored" data-anchor-id="marginal-vector-field">Marginal vector field</h3>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Note
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>It is an aggregation of the <img src="https://latex.codecogs.com/png.latex?u_t(.%20%5Cmid%20x%5E%7B(i)%7D_1)"> i.e.&nbsp;conditional vector field
<ul>
<li><img src="https://latex.codecogs.com/png.latex?u_t(x)%20=%20%5Cint%20u_t(x%20%5Cmid%20x_1)%20%5Cfrac%7Bp_t(x%20%5Cmid%20x_1)%20p_%7Bdata%7D(x_1)%7D%7Bp_t(x)%7Ddx_1"></li>
<li>where <img src="https://latex.codecogs.com/png.latex?%5Cfrac%7Bp_t(x%20%5Cmid%20x_1)%20p_%7Bdata%7D(x_1)%7D%7Bp_t(x)%7D%20=%20p(x_1%20%5Cmid%20x)"> i.e.&nbsp;Posterior mean which specifies where should we go given where we are right now.</li>
</ul></li>
</ul>
</div>
</div>
</section>
<section id="marginal-vector-fields-and-probability-path" class="level3">
<h3 class="anchored" data-anchor-id="marginal-vector-fields-and-probability-path">Marginal vector fields and probability path</h3>
<ul>
<li>Marginal Vector Fields [<img src="https://latex.codecogs.com/png.latex?u_t">] generates Marginal Probability Path [<img src="https://latex.codecogs.com/png.latex?p_t">]</li>
<li>Using continuity equation, we can derive:
<ul>
<li>if <img src="https://latex.codecogs.com/png.latex?x_0%20%5Csim%20p_0"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7Bdx_t%7D%7Bdt%7D%20=%20u_t(x_t)"> then</li>
<li><img src="https://latex.codecogs.com/png.latex?x_t%20%5Csim%20p_t"></li>
</ul></li>
</ul>
</section>
<section id="deriving-conditional-flow-matching" class="level3">
<h3 class="anchored" data-anchor-id="deriving-conditional-flow-matching">Deriving Conditional Flow Matching</h3>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?L_%7BFM%7D%20=%20%5Cmathbb%7BE%7D_%7Bt,%20x%7D%5B%7C%7Cu%5E%5Ctheta_t(x)%20-%20u_t(x)%7C%7C%5E2%5D"> is equivalent to <img src="https://latex.codecogs.com/png.latex?L_%7BCFM%7D%20=%20%5Cmathbb%7BE%7D_%7Bt,%20x_1,%20x%7D%5B%7C%7Cu%5E%5Ctheta_t(x)%20-%20u_t(x%20%5Cmid%20x_1)%7C%7C%5E2%5D"></li>
<li>Check out <a href="https://www.youtube.com/watch?v=7cMzfkWFWhI&amp;t=540s">this</a> to see why these two are equivalent</li>
<li>Now we have a tractable loss</li>
</ul>
</section>
<section id="training-procedure" class="level3">
<h3 class="anchored" data-anchor-id="training-procedure">Training Procedure</h3>
<ul>
<li>Sample noise <img src="https://latex.codecogs.com/png.latex?x_0%20%5Csim%20N(0,%20I)">, clean image <img src="https://latex.codecogs.com/png.latex?x_1%20%5Csim%20p_%7Bdata%7D"> and timestep <img src="https://latex.codecogs.com/png.latex?t%20%5Csim%20U%5B0,%201%5D"></li>
<li>Get noised image as: <img src="https://latex.codecogs.com/png.latex?x_t%20=%20(1-t)x_0%20+%20tx_1"></li>
<li>Use <img src="https://latex.codecogs.com/png.latex?x_t"> and <img src="https://latex.codecogs.com/png.latex?t"> to predict <img src="https://latex.codecogs.com/png.latex?x_1-x_0"> via <img src="https://latex.codecogs.com/png.latex?u%5E%5Ctheta_t(x_t)"></li>
<li>Compute loss <img src="https://latex.codecogs.com/png.latex?L%20=%20%7C%7Cu%5E%5Ctheta_t(x_t)%20-%20(x_1-x_0)%7C%7C%5E2"> and backpropagate through <img src="https://latex.codecogs.com/png.latex?u%5E%5Ctheta"></li>
</ul>
</section>
<section id="inference" class="level3">
<h3 class="anchored" data-anchor-id="inference">Inference</h3>
<ul>
<li>Sample noise <img src="https://latex.codecogs.com/png.latex?x_0%20%5Csim%20N(0,%20I)"></li>
<li>Use Euler to numerically solve the ODE
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x_%7Bt_i%7D%20=%20x_%7Bt_%7Bi-1%7D%7D%20+%20u%5E%5Ctheta_%7Bt_%7Bi-1%7D%7D(x_%7Bt_%7Bi-1%7D%7D)(t_i%20-%20t_%7Bi-1%7D)"></li>
</ul></li>
<li>Obtain final image <img src="https://latex.codecogs.com/png.latex?x_1"></li>
</ul>
</section>
<section id="issues-with-directly-using-flow-matching" class="level3">
<h3 class="anchored" data-anchor-id="issues-with-directly-using-flow-matching">Issues with directly using Flow Matching</h3>
<div class="callout callout-style-default callout-warning callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Warning
</div>
</div>
<div class="callout-body-container callout-body">
<figure style="text-align: left;" class="figure">
<img src="https://riteshrm.github.io/posts/flow-matching/fm_issue.png" style="width:40%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<ul>
<li>As we can see in above figure, two vector fields are intersecting each other, which means our vector field approximator will learn somewhat average of these two</li>
<li>And at inference time we will not be able to go to <img src="https://latex.codecogs.com/png.latex?x_1"> or <img src="https://latex.codecogs.com/png.latex?x%5E%7B'%7D_1">, we will go somewhere in between.</li>
<li>And also there is no linearity as it was in case of score based models, where we can deterministically compute the linear part</li>
</ul>
</div>
</div>
</section>
<section id="issues-with-flow-matching" class="level3">
<h3 class="anchored" data-anchor-id="issues-with-flow-matching">Issues with Flow Matching</h3>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Tip
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>Learning Complexity
<ul>
<li>Crossing paths leads to different learned rewiring</li>
<li>Problem even when paths are not strictly crossing</li>
</ul></li>
<li>Inefficiency at inference
<ul>
<li>Paths are not straight: needs more steps for approximation</li>
<li>No magic solver to save the day</li>
</ul></li>
</ul>
</div>
</div>
</section>
<section id="reflow" class="level3">
<h3 class="anchored" data-anchor-id="reflow">ReFlow</h3>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Note
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>So we got ReFlow, which tries to make paths more straighter</li>
<li>Reflow procedure</li>
<li>Train initial model which is called as 1-rectified flow</li>
<li>Use to create data pairs
<ul>
<li><img src="https://latex.codecogs.com/png.latex?D_%7Btrain%7D%20=%20U%5C%7Bz_0,%20z_1%5C%7D">, where <img src="https://latex.codecogs.com/png.latex?z_0%20%5Csim%20N(0,%20I)"> and <img src="https://latex.codecogs.com/png.latex?z_1%20=%20%5Cpsi%5E%5Ctheta_1(z_0)"></li>
</ul></li>
<li>Train on paired data, which is called as 2-rectified flow</li>
<li>Repeat 2-3 times as desired</li>
</ul>
</div>
</div>
</section>
</section>
<section id="implementation" class="level2">
<h2 class="anchored" data-anchor-id="implementation">Implementation</h2>
<div id="6c5a74c0" class="cell" data-execution_count="1">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb1" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb1-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb1-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb1-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb1-4"></span>
<span id="cb1-5"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> FlowMatching(nn.Module):</span>
<span id="cb1-6">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, velocity_predictor):</span>
<span id="cb1-7">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb1-8"></span>
<span id="cb1-9">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.velocity_predictor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> velocity_predictor</span>
<span id="cb1-10"></span>
<span id="cb1-11">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> flow_lerp(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_1):</span>
<span id="cb1-12">        bsz <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_1.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>]</span>
<span id="cb1-13">        t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.rand((bsz,)).to(x_1.device)</span>
<span id="cb1-14">        t_broadcast <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> t.view(bsz, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb1-15">        x_0 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn_like(x_1)</span>
<span id="cb1-16">        <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># the flow-matching lerp</span></span>
<span id="cb1-17">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> (<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> t_broadcast) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> x_0 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> t_broadcast <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> x_1</span>
<span id="cb1-18">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_0, x_t, t</span>
<span id="cb1-19">    </span>
<span id="cb1-20">    <span class="at" style="color: #657422;
background-color: null;
font-style: inherit;">@torch.no_grad</span>()</span>
<span id="cb1-21">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sample(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, shape, num_steps):</span>
<span id="cb1-22">        bsz <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>]</span>
<span id="cb1-23">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(shape, device<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.velocity_predictor.device)</span>
<span id="cb1-24">        delta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor([<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>num_steps] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> bsz).to(x_t.device).view([bsz, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>([<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">len</span>(x_t.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>:]))])</span>
<span id="cb1-25">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(num_steps):</span>
<span id="cb1-26">            t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor([i<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>num_steps] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> bsz).to(x_t.device)</span>
<span id="cb1-27">            predicted_velocity <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.velocity_predictor(x_t, t)</span>
<span id="cb1-28">            x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> predicted_velocity <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> delta_t</span>
<span id="cb1-29">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t</span>
<span id="cb1-30">    </span>
<span id="cb1-31">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> loss(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_1):</span>
<span id="cb1-32">        x_0, x_t, t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.flow_lerp(x_1)</span>
<span id="cb1-33">        target_velocity <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_1<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>x_0</span>
<span id="cb1-34">        predicted_velocity <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.velocity_predictor(x_t, t)</span>
<span id="cb1-35">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> torch.nn.functional.mse_loss(target_velocity, predicted_velocity)</span></code></pre></div></div>
</div>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/flow-matching/fm.gif" style="width:60%" class="figure-img">
<figcaption>
Flow matching samples from epoch 0 through training
</figcaption>
</figure>


</section>

 ]]></description>
  <category>Generative AI</category>
  <guid>https://riteshrm.github.io/posts/flow-matching/</guid>
  <pubDate>Tue, 02 Jun 2026 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/flow-matching/flow_matching_resized_thumbnail.png" medium="image" type="image/png" height="82" width="144"/>
</item>
<item>
  <title>Score Matching</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/score-matching/</link>
  <description><![CDATA[ 





<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Tip</span>References
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>This is mostly based on:
<ol type="1">
<li><a href="https://www.youtube.com/watch?v=_WaR2fjZpEQ">Stanford CME296 Diffusion &amp; Large Vision Models | Spring 2026 | Lecture 2 - Score matching</a></li>
<li><a href="https://www.youtube.com/watch?v=B4oHJpEJBAA">Diffusion Models From Scratch | Score-Based Generative Models Explained | Math Explained</a></li>
<li><a href="https://arxiv.org/abs/2011.13456">Score-Based Generative Modeling through Stochastic Differential Equations</a></li>
</ol></li>
</ul>
</div>
</div>
<hr>
<ul>
<li>Minimal PyTorch implementation accompanying these notes:
<ul>
<li><a href="https://github.com/riteshrm/nanoSBGM">nanoSBGM GitHub Repo</a></li>
</ul></li>
</ul>
<hr>
<section id="motivation" class="level2">
<h2 class="anchored" data-anchor-id="motivation">Motivation</h2>
<ul>
<li><strong>Objective:</strong> Given a complex data distribution how can we go from low probability to high probability</li>
<li><strong>Solution:</strong> Use gradient, which will guide to go towards high density</li>
<li>So if we somehow have access to the gradient of <img src="https://latex.codecogs.com/png.latex?p(x)"> i.e.&nbsp;data then we can use it.</li>
<li><img src="https://latex.codecogs.com/png.latex?p(x)%20=%20%5Cfrac%7Bf(x)%7D%7BZ%7D"></li>
<li>But according to property of probabilities
<ul>
<li><img src="https://latex.codecogs.com/png.latex?Z%20=%20%5Cint%20p_%7Bdata%7D(x)dx%20=%201"> which is intractable</li>
<li>Thus <img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_xp_%7Bdata%7D(x)%20=%20%5Ctriangledown_x%5Cfrac%7Bf(x)%7D%7BZ%7D"> is also intractable and also numerically unstable in low density regions</li>
</ul></li>
<li>So instead of that we can consider <img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_xlog(p_%7Bdata%7D(x))">
<ul>
<li>It is tractable
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_xlog(p_%7Bdata%7D(x))%20=%20%5Ctriangledown_xlog(f_%7Bdata%7D(x))%20-%20%5Ctriangledown_xlog(Z)"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_xlog(p_%7Bdata%7D(x))%20=%20%5Ctriangledown_xlog(f_%7Bdata%7D(x))"> since <img src="https://latex.codecogs.com/png.latex?Z"> is independent of x so it can be treated as constant.</li>
</ul></li>
<li>It Points in the same direction as <img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_xp_%7Bdata%7D(x)">
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctriangledown%20log(p)%20=%20%5Cfrac%7B%5Ctriangledown%20p%7D%7Bp%7D"></li>
</ul></li>
<li>Numerically stable
<ul>
<li>Since gradient depends on ratio of two numbers which are in similar range</li>
<li>Similar range because if <img src="https://latex.codecogs.com/png.latex?%5Ctriangledown%20p"> is small then there is possibility that p is also small</li>
</ul></li>
</ul></li>
<li>So we can follow the score i.e gradient of <img src="https://latex.codecogs.com/png.latex?log(p(x)"> with respect to x to move towards data points</li>
<li>It is possible that following the scores, we might always end up with data points which has high probability density and thus we might not be able to move to data points of low probability.</li>
</ul>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Note</span>Langevin Sampling
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>One solution is to use <strong>Langevin Sampling</strong>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x_t%20=%20x_%7Bt-1%7D%20+%20%5Cfrac%7B%5Calpha%7D%7B2%7D%5Ctriangledown_%7Bx%7Dlog(p_%7Bdata%7D(x_%7Bt-1%7D))%20+%20%5Csqrt%7B%5Calpha%7D%5Cepsilon_t"></li>
<li>where:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_%7Bx%7Dlog(p_%7Bdata%7D(x_%7Bt-1%7D))"> helps in going towards high density area</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Csqrt%7B%5Calpha%7D%5Cepsilon_t"> allows to explore the region</li>
</ul></li>
</ul></li>
</ul>
</div>
</div>
<ul>
<li><p>But we don’t have <img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_%7Bx%7Dlog(p_%7Bdata%7D(x_%7Bt-1%7D))">, so we try to estimate the score with <img src="https://latex.codecogs.com/png.latex?S_%7B%5Ctheta%7D(x)"></p></li>
<li><p>which gives:</p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?L_%7BSM%7D%20=%20%5Cmathbb%7BE%7D_%7Bx%7D%5B%7C%7CS_%7B%5Ctheta%7D(x)%20-%20%5Ctriangledown_%7Bx%7Dlog(p_%7Bdata%7D(x))%7C%7C%5E2%5D"></li>
</ul></li>
<li><p>But we don’t have access to <img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_%7Bx%7Dlog(p_%7Bdata%7D(x))"></p></li>
<li><p>There are various attempts to estimate the score, but let’s focus on more common one Denoising Score Matching</p></li>
</ul>
</section>
<section id="denoising-score-matching" class="level2">
<h2 class="anchored" data-anchor-id="denoising-score-matching">Denoising Score Matching</h2>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Note</span>Score of a Gaussian Distribution
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x%20%5Csim%20N(0,%20%5Csigma%5E2)"></li>
<li>Probability distribution function is
<ul>
<li><img src="https://latex.codecogs.com/png.latex?p(x)%20=%20%5Cfrac%7B1%7D%7B%5Csqrt%7B2%5Cpi%5Csigma%5E2%7D%7De%5E%7B%5Cfrac%7B-(x-%5Cmu)%5E2%7D%7B2%5Csigma%5E2%7D%7D"></li>
</ul></li>
<li>Score is:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?S(x)%20=%20-%5Cfrac%7Bx-%5Cmu%7D%7B%5Csigma%5E2%7D"></li>
</ul></li>
</ul>
</div>
</div>
<ul>
<li>The idea is to add noise to data, since we can get score of gaussian
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctilde%7Bx%7D%20=%20x%20+%20%5Csigma%5Cepsilon"> <img src="https://latex.codecogs.com/png.latex?%5Cepsilon%20%5Csim%20N(0,%20I)"></li>
</ul></li>
<li>Therefore:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?q_%5Csigma(%5Ctilde%7Bx%7D%20%5Cmid%20x)%20=%20N(0,%20%5Csigma%5E2I)"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_%7B%5Ctilde%7Bx%7D%7Dlog(q_%7B%5Csigma%7D(%5Ctilde%7Bx%7D%20%5Cmid%20x))%20=%20-%5Cfrac%7B%5Ctilde%7Bx%7D-x%7D%7B%5Csigma%5E2%7D"></li>
</ul></li>
<li>Adding noise to distribution
<ul>
<li><img src="https://latex.codecogs.com/png.latex?q_%7B%5Csigma%7D(%5Ctilde%7Bx%7D)%20=%20%5Cint%7Bq_%7B%5Csigma%7D(%5Ctilde%7Bx%7D%20%5Cmid%20x)p_%7Bdata%7D(x)dx%7D"></li>
<li>where <img src="https://latex.codecogs.com/png.latex?q_%7B%5Csigma%7D(%5Ctilde%7Bx%7D%20%5Cmid%20x)"> is perturbation kernel</li>
<li>It is basically take all the points from data sample and transform them into noisy samples where <img src="https://latex.codecogs.com/png.latex?%5Csigma"> tells how much noise you are adding</li>
</ul></li>
<li>Estimating the score of the noised distribution
<ul>
<li>Definition of score matching
<ul>
<li><img src="https://latex.codecogs.com/png.latex?L_%7BSM%7D(q_%7B%5Csigma%7D)%20=%20%5Cmathbb%7BE%7D_%7B%5Ctilde%7Bx%7D%7D%5B%7C%7CS_%7B%5Ctheta%7D(%5Ctilde%7Bx%7D)%20-%20%5Ctriangledown_%7B%5Ctilde%7Bx%7D%7Dlog(q_%7B%5Csigma%7D(%5Ctilde%7Bx%7D))%7C%7C%5E2%5D"></li>
</ul></li>
<li>From some <a href="https://www.youtube.com/watch?v=B4oHJpEJBAA&amp;t=810s">maths</a>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?L_%7BSM%7D(q_%7B%5Csigma%7D)%20=%20%5Cmathbb%7BE%7D_%7B%5Ctilde%7Bx%7D%7D%5B%7C%7CS_%7B%5Ctheta%7D(%5Ctilde%7Bx%7D)%20-%20%5Ctriangledown_%7B%5Ctilde%7Bx%7D%7Dlog(q_%7B%5Csigma%7D(%5Ctilde%7Bx%7D%20%5Cmid%20x))%7C%7C%5E2%5D"></li>
<li>where <img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_%7B%5Ctilde%7Bx%7D%7Dlog(q_%7B%5Csigma%7D(%5Ctilde%7Bx%7D%20%5Cmid%20x))"> is tractable and equal to <img src="https://latex.codecogs.com/png.latex?-%5Cfrac%7B%5Ctilde%7Bx%7D-x%7D%7B%5Csigma%5E2%7D"></li>
</ul></li>
</ul></li>
<li>We now have a tractable loss</li>
<li>However in <img src="https://latex.codecogs.com/png.latex?L_%7BSM%7D(q_%7B%5Csigma%7D)">, <img src="https://latex.codecogs.com/png.latex?q_%7B%5Csigma%7D"> is not exactly <img src="https://latex.codecogs.com/png.latex?p_%7Bdata%7D">
<ul>
<li>let’s say we used <img src="https://latex.codecogs.com/png.latex?%5Csigma%20%3C%3C%201">:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?q_%7B%5Csigma%7D"> will be close to <img src="https://latex.codecogs.com/png.latex?p_%7Bdata%7D"> but poor estimation in low density regions.</li>
</ul></li>
<li>if we use <img src="https://latex.codecogs.com/png.latex?%5Csigma%20%3E%3E%201">:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?q_%7B%5Csigma%7D"> will be far from <img src="https://latex.codecogs.com/png.latex?p_%7Bdata%7D"> but good estimations in low density regions.</li>
</ul></li>
</ul></li>
<li>So how do we achieve best of both worlds
<ul>
<li>The idea is to have score matching with varying noise</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Csigma_%7B1%7D%20%3C%20%5Csigma_%7B2%7D%20...%20%3C%20%5Csigma_%7BT%7D"></li>
<li><img src="https://latex.codecogs.com/png.latex?S_%7B%5Ctheta%7D(x)%20-%3E%20S_%7B%5Ctheta%7D(x,%20%5Csigma_%7Bi%7D)"></li>
<li>which gives loss as:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?L_%7BNCSN%7D%20=%20%5Csum_%7Bi=1%7D%5E%7BL%7D%20%5Clambda(i)%5Cmathbb%7BE%7D_%7Bx%7D%5B%7C%7CS_%7B%5Ctheta%7D(x,%20%5Csigma_i)%20-%20%5Ctriangledown_%7Bx%7Dlog(q_%7B%5Csigma_i%7D(x))%7C%7C%5E2%5D">. NCSN: Noise Conditioned Score Network</li>
</ul></li>
</ul></li>
<li>Now we got the score approximator as <img src="https://latex.codecogs.com/png.latex?S_%7B%5Ctheta%7D(x,%20%5Csigma_i)">, how can we use this to generate samples</li>
</ul>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Note</span>Annealed Langevin Dynamics
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>We can use <strong>Annealed Langevin Dynamics</strong> (Sampling with varied noise levels)
<ol type="1">
<li>Sample: <img src="https://latex.codecogs.com/png.latex?Noise%20%5Csim%20N(0,%20%5Csigma_%7BT%7D%5E2I)"></li>
<li>For each <img src="https://latex.codecogs.com/png.latex?%5Csigma_i">, perform iterative update for K steps
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x"> &lt;- <img src="https://latex.codecogs.com/png.latex?x%20+%20%5Cfrac%7B%5Calpha_i%7D%7B2%7DS_%7B%5Ctheta%7D(x,%20%5Csigma_i)%20+%20%5Csqrt%7B%5Calpha_i%7D%5Cepsilon"></li>
</ul></li>
<li>Obtain final image <img src="https://latex.codecogs.com/png.latex?x_0"></li>
</ol></li>
</ul>
</div>
</div>
<ul>
<li>But in above cases, first of all we need to define T, which will be responsible for discretizing the noising process.</li>
<li>And also if somehow we can make this process evolve in continuous time instead of discrete ones then we can use differential equations efficiently.</li>
</ul>
</section>
<section id="from-discrete-to-continuous" class="level2">
<h2 class="anchored" data-anchor-id="from-discrete-to-continuous">From Discrete to Continuous</h2>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Note</span>Wiener Processes
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>Continuous equivalent of adding incremental gaussian noise</li>
<li>Stochastic process with following properties:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?w_0%20=%200"></li>
<li><img src="https://latex.codecogs.com/png.latex?w_t%20-%20w_s%20%5Csim%20N(0,%20(t-s)I)"></li>
<li>Independent increment (<img src="https://latex.codecogs.com/png.latex?w_t"> or <img src="https://latex.codecogs.com/png.latex?w_s"> doesn’t depend on what happened before)</li>
</ul></li>
</ul>
</div>
</div>
<ul>
<li>Lets make discrete DDPM into continuous one</li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7Bt%7D%20=%20%5Csqrt%7B1-%5Cbeta_%7Bt%7D%7Dx_%7Bt-1%7D%20+%20%5Csqrt%5Cbeta_%7Bt%7D%20%5Cepsilon"></li>
<li>We want a differential evolution in x as function f everything else.</li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7Bt%7D%20-%20%20x_%7Bt-1%7D=%20%5B%5Csqrt%7B1-%5Cbeta_%7Bt%7D%7D-1%5Dx_%7Bt-1%7D%20+%20%5Csqrt%5Cbeta_%7Bt%7D%20%5Cepsilon"></li>
<li>Lets make <img src="https://latex.codecogs.com/png.latex?%5Cbeta_t"> as function of t
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cbeta_t%20=%20%5Cbeta(t)dt"></li>
<li>where
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cbeta_t">: Noise we add between two discrete steps</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cbeta(t)">: rate of noise at t</li>
<li><img src="https://latex.codecogs.com/png.latex?dt">: Increment of time</li>
</ul></li>
</ul></li>
<li>Now replace <img src="https://latex.codecogs.com/png.latex?%5Cbeta_t"> with <img src="https://latex.codecogs.com/png.latex?%5Cbeta(t)dt">, which gives
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x_%7Bt%7D%20-%20%20x_%7Bt-1%7D=%20%5B%5Csqrt%7B1-%5Cbeta(t)dt%7D-1%5Dx_%7Bt-1%7D%20+%20%5Csqrt%7B%5Cbeta(t)dt%7D%20%5Cepsilon"></li>
</ul></li>
<li>If <img src="https://latex.codecogs.com/png.latex?%5Ctriangle_t"> -&gt; 0, then <img src="https://latex.codecogs.com/png.latex?x_%7Bt%7D%20-%20%20x_%7Bt-1%7D%20=%20dx"> (Differential Evolution)</li>
<li>Using Taylor expansion and wiener process, we can approximate first and second term respectively
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Csqrt%7B1-%5Cbeta(t)dt%7D%20%5Csim%201-%5Cfrac%7B1%7D%7B2%7D%5Cbeta(t)dt"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Csqrt%7Bdt%7D%20%5Cepsilon%20%5Csim%20dw"></li>
</ul></li>
<li><img src="https://latex.codecogs.com/png.latex?dx%20=%20-%5Cfrac%7B1%7D%7B2%7D%5Cbeta(t)xdt%20+%20%5Csqrt%7B%5Cbeta(t)%7Ddw"></li>
<li><img src="https://latex.codecogs.com/png.latex?dx%20=%20f(x,%20t)dt%20+%20g(t)dw">
<ul>
<li>Where
<ul>
<li><img src="https://latex.codecogs.com/png.latex?f(x,%20t)"> is drift coefficient which is deterministic</li>
<li><img src="https://latex.codecogs.com/png.latex?g(t)"> is diffusion coefficient which is stochastic</li>
</ul></li>
</ul></li>
<li>SDE Variants</li>
</ul>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Note</span>Common SDE Variants
</div>
</div>
<div class="callout-body-container callout-body">
<table class="caption-top table">
<colgroup>
<col style="width: 50%">
<col style="width: 50%">
</colgroup>
<thead>
<tr class="header">
<th style="text-align: center;">Variance Preserving</th>
<th style="text-align: center;">Variance Exploding</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td style="text-align: center;">Ex: DDPM</td>
<td style="text-align: center;">Ex:NCSN</td>
</tr>
<tr class="even">
<td style="text-align: center;"><img src="https://latex.codecogs.com/png.latex?f(x,%20t)%20=%20-%5Cfrac%7B1%7D%7B2%7D%5Cbeta(t)x"></td>
<td style="text-align: center;"><img src="https://latex.codecogs.com/png.latex?f(x,%20t)%20=%200"></td>
</tr>
<tr class="odd">
<td style="text-align: center;"><img src="https://latex.codecogs.com/png.latex?g(t)%20=%20%5Csqrt%7B%5Cbeta(t)%7D"></td>
<td style="text-align: center;"><img src="https://latex.codecogs.com/png.latex?g(t)%20=%20%5Csqrt%7B%5Cfrac%7Bd%5B%5Csigma%5E2(t)%5D%7D%7Bdt%7D%7D"></td>
</tr>
</tbody>
</table>
</div>
</div>
<ul>
<li>Generalised training objective
<ul>
<li><img src="https://latex.codecogs.com/png.latex?L_%7BDSM%7D%20=%20%5Cmathbb%7BE%7D_%7Bt,%20x_0,%20x_t%7D%5B%5Clambda_t%7C%7CS_%7B%5Ctheta%7D(x_t,%20t)%20-%20%5Ctriangledown_%7Bx_t%7Dlog(p(x_t%20%7C%20x_0))%7C%7C%5E2%5D">
<ul>
<li>where <img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_%7Bx_t%7Dlog(p(x_t%20%7C%20x_0))%20=%20-%5Cfrac%7B%5Cepsilon%7D%7B%5Csigma_t%7D"></li>
</ul></li>
</ul></li>
<li>Training a generalised score model
<ol type="1">
<li>Sample <img src="https://latex.codecogs.com/png.latex?x_0(data)%20%5Csim%20p_%7Bdata%7D">, <img src="https://latex.codecogs.com/png.latex?%5Cepsilon(noise)%20%5Csim%20N(0,%20I)"> and <img src="https://latex.codecogs.com/png.latex?t(timestep)%20%5Csim%20U(0,%20T)"></li>
<li>Create a noisy sample
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x_t%20=%20%5Calpha_t%20x_0%20+%20%5Csigma_t%20%5Cepsilon">. where <img src="https://latex.codecogs.com/png.latex?%5Calpha_t"> and <img src="https://latex.codecogs.com/png.latex?%5Csigma_t"> can be defined based on the variant of SDE</li>
</ul></li>
<li>Use <img src="https://latex.codecogs.com/png.latex?x_t"> and <img src="https://latex.codecogs.com/png.latex?t"> to predict <img src="https://latex.codecogs.com/png.latex?-%5Cfrac%7B%5Cepsilon%7D%7B%5Csigma_t%7D"> via <img src="https://latex.codecogs.com/png.latex?S_%7B%5Ctheta%7D(x_t,%20t)"></li>
<li>Compute Loss and backpropagate
<ul>
<li><img src="https://latex.codecogs.com/png.latex?L%20=%20%5Clambda_t%7C%7CS_%7B%5Ctheta%7D(x_t,%20t)%20+%20%5Cfrac%7B%5Cepsilon%7D%7B%5Csigma_t%7D%7C%7C%5E2"></li>
</ul></li>
</ol></li>
<li>Inference of trained model
<ul>
<li>Forward process: Perturb data into noise
<ul>
<li><img src="https://latex.codecogs.com/png.latex?dx%20=%20f(x,%20t)dt%20+%20g(t)dw"></li>
</ul></li>
<li>Reverse process: noise back to data
<ul>
<li><img src="https://latex.codecogs.com/png.latex?dx%20=%20%5Bf(x,%20t)%20-%20g(t)%5E2%5Ctriangledown_xlog(p_%7Bt%7D(x)%5Ddt%20+%20g(t)d%5Cbar%7Bw%7D">. This derived using Fokker-Planck equation</li>
</ul></li>
<li>Intuition of above equation
<ul>
<li><img src="https://latex.codecogs.com/png.latex?f(x,%20t)">: forward drift coefficient</li>
<li><img src="https://latex.codecogs.com/png.latex?g(t)">: forward diffusion coefficient</li>
<li><img src="https://latex.codecogs.com/png.latex?d%5Cbar%7Bw%7D">: Wiener process but different than forward one</li>
<li><img src="https://latex.codecogs.com/png.latex?g(t)%5E2%5Ctriangledown_xlog(p_%7Bt%7D(x))">: correction to drift coefficient</li>
<li>Basically in forward process we diffused from data to noise and to go back we need some corrections.</li>
</ul></li>
</ul></li>
<li>Sampling using Euler-Maruyama
<ol type="1">
<li>Sample Noise i.e.&nbsp;<img src="https://latex.codecogs.com/png.latex?x_T%20%5Csim%20N(0,%20%5Csigma_T%5E2I)"></li>
<li>Use Euler-Maruyama to go through reverse SDE
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x_%7Bt_%7Bi-1%7D%7D%20=%20x_%7Bt_i%7D%20+%20%5Bf(x_%7Bt_i%7D,%20t_i)%20-%20g(t_i)%5E2S_%5Ctheta(x_%7Bt_i%7D,%20t_i)%5D%5Ctriangle%20t%20+%20g(t_i)%5Csqrt%7B%5Ctriangle%20t%7D%5Cepsilon"></li>
</ul></li>
<li>Obtain final sample <img src="https://latex.codecogs.com/png.latex?x_0"></li>
</ol></li>
<li>getting <img src="https://latex.codecogs.com/png.latex?%5Cbeta(t)">
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cbeta(t)%20=%20%5Cbeta_%7Bmin%7D%20+%20t%20*%20(%5Cbeta_%7Bmax%7D%20-%20%5Cbeta_%7Bmin%7D)"></li>
<li>So <img src="https://latex.codecogs.com/png.latex?%5Cint_%7B0%7D%5E%7Bt%7D%5Cbeta(s)ds%20=%20%5Cbeta_%7Bmin%7D*t%20+%200.5%20*%20(%5Cbeta_%7Bmax%7D%20-%20%5Cbeta_%7Bmin%7D)*%20t**2"></li>
</ul></li>
<li>Limitations of SDE
<ul>
<li>Stochastic term as <img src="https://latex.codecogs.com/png.latex?g(t)d%5Cbar%7Bw%7D"> means:
<ul>
<li>Slower solver: Need 1000-2000 steps</li>
<li>More source of error: Discretization as well as injected stochastic noise</li>
</ul></li>
</ul></li>
</ul>
</section>
<section id="probability-flow-ode" class="level2">
<h2 class="anchored" data-anchor-id="probability-flow-ode">Probability Flow ODE</h2>
<ul>
<li>Hypothetically write SDE as an ODE
<ul>
<li><img src="https://latex.codecogs.com/png.latex?dx%20=%20%5BSomething%5Ddt%20+%20%5Cphi">, where <img src="https://latex.codecogs.com/png.latex?%5Cphi"> is null</li>
<li>No stochastic term means:
<ul>
<li>Faster solver: leverage mathematical properties to go fast vs slow</li>
<li>Focused source of error: Now we will have error from discretization only</li>
</ul></li>
</ul></li>
<li>Lets derive ODE</li>
<li>Forward SDE: <img src="https://latex.codecogs.com/png.latex?dx%20=%20f(x,%20t)dt%20+%20g(t)dw"></li>
<li>Probability flow of x at t using Fokker-Planck Equation on forward SDE gives:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7B%5Cdelta%20p_t(x)%7D%7B%5Cdelta%20t%7D%20=%20-%5Ctriangledown(f(x,%20t)p_t(x))%20+%20%5Cfrac%7B1%7D%7B2%7Dg(t)%5E2%20%5Ctriangledown%20p_t(x)"></li>
</ul></li>
<li>After applying some algebraic operations, we get continuity equation as:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7B%5Cdelta%20p%7D%7B%5Cdelta%20t%7D(x)%20=%20-%5Ctriangledown%5Bf(x,%20t)%20-%20%5Cfrac%7B1%7D%7B2%7Dg(t)%5E2%20%5Ctriangledown_x%20log(p_t(x))%5Dp_t(x)"></li>
<li>where
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Bf(x,%20t)%20-%20%5Cfrac%7B1%7D%7B2%7Dg(t)%5E2%20%5Ctriangledown_x%20log(p_t(x))%5D"> is velocity of probability flow</li>
</ul></li>
</ul></li>
<li>So we got PF-ODE as <img src="https://latex.codecogs.com/png.latex?dx%20=%20v(x,%20t)dt"> and <img src="https://latex.codecogs.com/png.latex?v(x,%20t)%20=%20%5Bf(x,%20t)%20-%20%5Cfrac%7B1%7D%7B2%7Dg(t)%5E2%20%5Ctriangledown_x%20log(p_t(x))%5D">
<ul>
<li>where:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?f(x,%20t)"> and <img src="https://latex.codecogs.com/png.latex?g(t)%5E2"> are modeling assumptions</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctriangledown_x%20log(p_t(x))"> is score approximated by the model</li>
</ul></li>
</ul></li>
<li>In above formulation, the Probability Flow is preserved between reverse SDE and reverse ODE but the trajectories are different</li>
</ul>
</section>
<section id="implementation" class="level2">
<h2 class="anchored" data-anchor-id="implementation">Implementation</h2>
<section id="vpsde" class="level3">
<h3 class="anchored" data-anchor-id="vpsde">VPSDE</h3>
<ul>
<li>How to get <img src="https://latex.codecogs.com/png.latex?x_t">
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x_t%20=%20x_0%20*%20%5Calpha_t%20+%20%5Cepsilon%20*%20%5Csigma_t"></li>
<li>Where:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Calpha_t%20=%20e%5E%7B-%5Cfrac%7B1%7D%7B2%7D%20%5Cint_%7B0%7D%5E%7Bt%7D%5Cbeta(s)ds%7D"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Csigma_t%20=%20%5Csqrt%7B1%20-%20e%5E%7B-%5Cint_%7B0%7D%5E%7Bt%7D%5Cbeta(s)ds%7D%7D"></li>
</ul></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cbeta(t)%20=%20%5Cbeta_%7Bmin%7D%20+%20t*(%5Cbeta_%7Bmax%7D%20-%20%5Cbeta_%7Bmin%7D)"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cint_%7B0%7D%5E%7Bt%7D%5Cbeta(s)ds%20=%20%5Cbeta_%7Bmin%7D%20*%20t%20+%200.%205*%20(%5Cbeta_%7Bmax%7D%20-%20%5Cbeta_%7Bmin%7D)%20*%20t%5E2"></li>
</ul></li>
<li>Drift and Diffusion Coefficient
<ul>
<li><img src="https://latex.codecogs.com/png.latex?f(x,t)%20=%20-%5Cfrac%7B1%7D%7B2%7D%5Cbeta(t)x"></li>
<li><img src="https://latex.codecogs.com/png.latex?g(t)%20=%20%5Csqrt%7B%5Cbeta(t)%7D"></li>
</ul></li>
</ul>
<div id="9152406d" class="cell" data-execution_count="1">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb1" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb1-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb1-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb1-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb1-4"></span>
<span id="cb1-5"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> VPSDE(nn.Module):</span>
<span id="cb1-6">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, beta_min, beta_max, eps, score_model):</span>
<span id="cb1-7">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb1-8">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_min <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> beta_min</span>
<span id="cb1-9">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> beta_max</span>
<span id="cb1-10">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> eps</span>
<span id="cb1-11">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> score_model</span>
<span id="cb1-12">    </span>
<span id="cb1-13">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_integrated_beta_t(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, t):</span>
<span id="cb1-14">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_min<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> (<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_min) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> t<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span></span>
<span id="cb1-15">    </span>
<span id="cb1-16">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_beta_t(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, t):</span>
<span id="cb1-17">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_min <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_min) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> t</span>
<span id="cb1-18"></span>
<span id="cb1-19">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_integrated_alpha_t(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, t):</span>
<span id="cb1-20">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> torch.exp(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_integrated_beta_t(t))</span>
<span id="cb1-21">    </span>
<span id="cb1-22">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_integrated_sigma_t(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, t):</span>
<span id="cb1-23">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> torch.sqrt(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> torch.exp(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_integrated_beta_t(t)))</span>
<span id="cb1-24">    </span>
<span id="cb1-25">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> perturbation_kernel(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_0, t, noise<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>):</span>
<span id="cb1-26">        alpha_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_integrated_alpha_t(t).view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb1-27">        sigma_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_integrated_sigma_t(t).view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb1-28">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> noise <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>:</span>
<span id="cb1-29">            noise <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn_like(x_0)</span>
<span id="cb1-30">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> alpha_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> x_0 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> sigma_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> noise</span>
<span id="cb1-31">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t, noise, sigma_t</span>
<span id="cb1-32">    </span>
<span id="cb1-33">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sde(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x, t):</span>
<span id="cb1-34">        drift <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_beta_t(t).view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> x</span>
<span id="cb1-35">        diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.sqrt(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_beta_t(t)).view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb1-36">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> drift, diffusion</span>
<span id="cb1-37">    </span>
<span id="cb1-38">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sample(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, shape, y, num_steps):</span>
<span id="cb1-39">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(shape)</span>
<span id="cb1-40">        ts <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.linspace(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps, num_steps)</span>
<span id="cb1-41">        delta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>num_steps</span>
<span id="cb1-42">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> t <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> ts:</span>
<span id="cb1-43">            score <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model(x_t, t.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>), y)</span>
<span id="cb1-44">            drift, diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sde(x_t, t)</span>
<span id="cb1-45">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (drift <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> diffusion<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>score) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> delta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> torch.sqrt(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>delta_t)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>torch.randn_like(x_t)</span>
<span id="cb1-46">            x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_prevt</span>
<span id="cb1-47">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t</span>
<span id="cb1-48">    </span>
<span id="cb1-49">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sample_pf_ode(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, shape, y, num_steps):</span>
<span id="cb1-50">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(shape)</span>
<span id="cb1-51">        ts <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.linspace(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps, num_steps)</span>
<span id="cb1-52">        delta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>num_steps</span>
<span id="cb1-53">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> t <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> ts:</span>
<span id="cb1-54">            score <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model(x_t, t.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>), y)</span>
<span id="cb1-55">            drift, diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sde(x_t, t)</span>
<span id="cb1-56">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (drift <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>diffusion<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>score) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> delta_t</span>
<span id="cb1-57">            x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_prevt</span>
<span id="cb1-58">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t</span>
<span id="cb1-59"></span>
<span id="cb1-60">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> loss(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, batch):</span>
<span id="cb1-61">        x_0, y <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> batch</span>
<span id="cb1-62">        t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>torch.rand((x_0.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>], ))</span>
<span id="cb1-63">        x_t, noise, sigma_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.perturbation_kernel(x_0, t)</span>
<span id="cb1-64">        s_theta <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model(x_t, t.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>), y)</span>
<span id="cb1-65">        loss <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> F.mse_loss(s_theta, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>noise<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>sigma_t, reduction<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'mean'</span>)</span>
<span id="cb1-66">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> loss</span></code></pre></div></div>
</div>
</section>
<section id="sub-vpsde" class="level3">
<h3 class="anchored" data-anchor-id="sub-vpsde">sub-VPSDE</h3>
<ul>
<li>How to get <img src="https://latex.codecogs.com/png.latex?x_t">
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x_t%20=%20x_0%20*%20%5Calpha_t%20+%20%5Cepsilon%20*%20%5Csigma_t"></li>
<li>Where:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Calpha_t%20=%20e%5E%7B-%5Cfrac%7B1%7D%7B2%7D%20%5Cint_%7B0%7D%5E%7Bt%7D%5Cbeta(s)ds%7D"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Csigma_t%20=%201%20-%20e%5E%7B-%5Cint_%7B0%7D%5E%7Bt%7D%5Cbeta(s)ds%7D"></li>
</ul></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cbeta(t)%20=%20%5Cbeta_%7Bmin%7D%20+%20t*(%5Cbeta_%7Bmax%7D%20-%20%5Cbeta_%7Bmin%7D)"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cint_%7B0%7D%5E%7Bt%7D%5Cbeta(s)ds%20=%20%5Cbeta_%7Bmin%7D%20*%20t%20+%200.%205*%20(%5Cbeta_%7Bmax%7D%20-%20%5Cbeta_%7Bmin%7D)%20*%20t%5E2"></li>
</ul></li>
<li>Drift and Diffusion Coefficient
<ul>
<li><img src="https://latex.codecogs.com/png.latex?f(x,t)%20=%20-%5Cfrac%7B1%7D%7B2%7D%5Cbeta(t)x"></li>
<li><img src="https://latex.codecogs.com/png.latex?g(t)%20=%20%5Csqrt%7B%5Cbeta(t)%20(1-e%5E%7B-2%5Cint_%7B0%7D%5E%7Bt%7D%5Cbeta(s)ds%7D)%7D"></li>
</ul></li>
</ul>
<div id="23fff625" class="cell" data-execution_count="2">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb2" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb2-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb2-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb2-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb2-4"></span>
<span id="cb2-5"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> subVPSDE(nn.Module):</span>
<span id="cb2-6">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, beta_min, beta_max, eps, score_model):</span>
<span id="cb2-7">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb2-8">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_min <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> beta_min</span>
<span id="cb2-9">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> beta_max</span>
<span id="cb2-10">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> eps</span>
<span id="cb2-11">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> score_model</span>
<span id="cb2-12">    </span>
<span id="cb2-13">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_integrated_beta_t(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, t):</span>
<span id="cb2-14">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_min<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> (<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_min) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> t<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span></span>
<span id="cb2-15">    </span>
<span id="cb2-16">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_beta_t(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, t):</span>
<span id="cb2-17">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_min <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_min) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> t</span>
<span id="cb2-18"></span>
<span id="cb2-19">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_integrated_alpha_t(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, t):</span>
<span id="cb2-20">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> torch.exp(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_integrated_beta_t(t))</span>
<span id="cb2-21">    </span>
<span id="cb2-22">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_integrated_sigma_t(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, t):</span>
<span id="cb2-23">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> torch.exp(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_integrated_beta_t(t))</span>
<span id="cb2-24">    </span>
<span id="cb2-25">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> perturbation_kernel(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_0, t, noise<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>):</span>
<span id="cb2-26">        alpha_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_integrated_alpha_t(t).view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb2-27">        sigma_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_integrated_sigma_t(t).view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb2-28">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> noise <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>:</span>
<span id="cb2-29">            noise <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn_like(x_0)</span>
<span id="cb2-30">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> alpha_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> x_0 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> sigma_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> noise</span>
<span id="cb2-31">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t, noise, sigma_t</span>
<span id="cb2-32">    </span>
<span id="cb2-33">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sde(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x, t):</span>
<span id="cb2-34">        drift <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> (<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_beta_t(t) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> x).view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb2-35">        diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.sqrt(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_beta_t(t)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>torch.exp(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_integrated_beta_t(t)))).view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb2-36">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> drift, diffusion</span>
<span id="cb2-37">    </span>
<span id="cb2-38">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sample(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, shape, y, num_steps):</span>
<span id="cb2-39">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(shape)</span>
<span id="cb2-40">        ts <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.linspace(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps, num_steps)</span>
<span id="cb2-41">        delta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>num_steps</span>
<span id="cb2-42">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> t <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> ts:</span>
<span id="cb2-43">            score <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model(x_t, t.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>), y)</span>
<span id="cb2-44">            drift, diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sde(x_t, t)</span>
<span id="cb2-45">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (drift <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> diffusion<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>score) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> delta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> torch.sqrt(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>delta_t)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>torch.randn_like(x_t)</span>
<span id="cb2-46">            x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_prevt</span>
<span id="cb2-47">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t</span>
<span id="cb2-48">    </span>
<span id="cb2-49">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sample_pf_ode(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, shape, y, num_steps):</span>
<span id="cb2-50">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(shape)</span>
<span id="cb2-51">        ts <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.linspace(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps, num_steps)</span>
<span id="cb2-52">        delta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>num_steps</span>
<span id="cb2-53">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> t <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> ts:</span>
<span id="cb2-54">            score <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model(x_t, t.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>), y)</span>
<span id="cb2-55">            drift, diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sde(x_t, t)</span>
<span id="cb2-56">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (drift <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>diffusion<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>score) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> delta_t</span>
<span id="cb2-57">            x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_prevt</span>
<span id="cb2-58">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t</span>
<span id="cb2-59"></span>
<span id="cb2-60">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> loss(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, batch):</span>
<span id="cb2-61">        x_0, y <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> batch</span>
<span id="cb2-62">        t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>torch.rand((x_0.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>], ))</span>
<span id="cb2-63">        x_t, noise, sigma_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.perturbation_kernel(x_0, t)</span>
<span id="cb2-64">        s_theta <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model(x_t, t.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>), y)</span>
<span id="cb2-65">        loss <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> F.mse_loss(s_theta, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>noise<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>sigma_t, reduction<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'mean'</span>)</span>
<span id="cb2-66">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> loss</span></code></pre></div></div>
</div>
</section>
<section id="vesde" class="level3">
<h3 class="anchored" data-anchor-id="vesde">VESDE</h3>
<ul>
<li>How to get <img src="https://latex.codecogs.com/png.latex?x_t">
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x_t%20=%20x_0%20+%20%5Cepsilon%20*%20%5Csigma_t"></li>
<li>Where:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Csigma_t%20=%20%5Csigma_%7Bmin%7D(%5Cfrac%7B%5Csigma_%7Bmax%7D%7D%7B%5Csigma_%7Bmin%7D%7D)%5Et"></li>
</ul></li>
</ul></li>
<li>Drift and Diffusion Coefficient
<ul>
<li><img src="https://latex.codecogs.com/png.latex?f(x,t)%20=%200"></li>
<li><img src="https://latex.codecogs.com/png.latex?g(t)%20=%20%5Csqrt%7B%5Cfrac%7Bd%5B%5Csigma%5E2(t)%5D%7D%7Bdt%7D%7D%20=%20%5Csigma_t%20%5Csqrt%7B2log%5Cfrac%7B%5Csigma_%7Bmax%7D%7D%7B%5Csigma_%7Bmin%7D%7D%7D"></li>
</ul></li>
</ul>
<div id="68b8fbab" class="cell" data-execution_count="3">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb3" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb3-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb3-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb3-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb3-4"></span>
<span id="cb3-5"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> VESDE(nn.Module):</span>
<span id="cb3-6">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, sigma_min, sigma_max, eps, score_model):</span>
<span id="cb3-7">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb3-8">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sigma_min <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> sigma_min</span>
<span id="cb3-9">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sigma_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> sigma_max</span>
<span id="cb3-10">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> score_model</span>
<span id="cb3-11">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> eps</span>
<span id="cb3-12">    </span>
<span id="cb3-13">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_sigma_t(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, t):</span>
<span id="cb3-14">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sigma_min<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>((<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sigma_max<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sigma_min) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span>t)</span>
<span id="cb3-15">    </span>
<span id="cb3-16">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> perturbation_kernel(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_0, t, noise<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>):</span>
<span id="cb3-17">        sigma_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_sigma_t(t).view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb3-18">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> noise <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>:</span>
<span id="cb3-19">            noise <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn_like(x_0)</span>
<span id="cb3-20">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_0 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> sigma_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> noise</span>
<span id="cb3-21">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t, noise, sigma_t</span>
<span id="cb3-22">    </span>
<span id="cb3-23">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sde(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x, t):</span>
<span id="cb3-24">        drift <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.zeros_like(x)</span>
<span id="cb3-25">        diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> (<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.get_sigma_t(t) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> torch.sqrt(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>torch.log(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sigma_max<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sigma_min))).view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb3-26">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> drift, diffusion</span>
<span id="cb3-27">    </span>
<span id="cb3-28">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sample(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, shape, y, num_steps):</span>
<span id="cb3-29">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(shape)</span>
<span id="cb3-30">        ts <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.linspace(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps, num_steps)</span>
<span id="cb3-31">        delta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>num_steps</span>
<span id="cb3-32">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> t <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> ts:</span>
<span id="cb3-33">            score <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model(x_t, t.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>), y)</span>
<span id="cb3-34">            drift, diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sde(x_t, t)</span>
<span id="cb3-35">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (drift <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> diffusion<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>score) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> delta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> torch.sqrt(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>delta_t)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>torch.randn_like(x_t)</span>
<span id="cb3-36">            x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_prevt</span>
<span id="cb3-37">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t</span>
<span id="cb3-38">    </span>
<span id="cb3-39">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sample_pf_ode(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, shape, y, num_steps):</span>
<span id="cb3-40">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(shape)</span>
<span id="cb3-41">        ts <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.linspace(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps, num_steps)</span>
<span id="cb3-42">        delta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>num_steps</span>
<span id="cb3-43">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> t <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> ts:</span>
<span id="cb3-44">            score <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model(x_t, t.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>), y)</span>
<span id="cb3-45">            drift, diffusion <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sde(x_t, t)</span>
<span id="cb3-46">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (drift <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>diffusion<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>score) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> delta_t</span>
<span id="cb3-47">            x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_prevt</span>
<span id="cb3-48">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t</span>
<span id="cb3-49"></span>
<span id="cb3-50">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> loss(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, batch):</span>
<span id="cb3-51">        x_0, y <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> batch</span>
<span id="cb3-52">        t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>torch.rand((x_0.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>], ))</span>
<span id="cb3-53">        x_t, noise, sigma_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.perturbation_kernel(x_0, t)</span>
<span id="cb3-54">        s_theta <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.score_model(x_t, t.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>), y)</span>
<span id="cb3-55">        loss <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> F.mse_loss(s_theta, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>noise<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>sigma_t, reduction<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'mean'</span>)</span>
<span id="cb3-56">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> loss</span></code></pre></div></div>
</div>


</section>
</section>

 ]]></description>
  <category>Generative AI</category>
  <guid>https://riteshrm.github.io/posts/score-matching/</guid>
  <pubDate>Fri, 22 May 2026 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/score-matching/score_resized_thumbnail.png" medium="image" type="image/png" height="82" width="144"/>
</item>
<item>
  <title>Diffusion Models</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/diffusion-models/</link>
  <description><![CDATA[ 





<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Tip</span>References
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>This is mostly based on:
<ol type="1">
<li><a href="https://www.youtube.com/watch?v=tr-CUpw--ck">Stanford CME296 Diffusion &amp; Large Vision Models | Spring 2026 | Lecture 1 - Diffusion</a></li>
<li><a href="https://www.youtube.com/watch?v=HoKDTa5jHvg&amp;t=1409s">Diffusion Models | Paper Explanation | Math Explained</a></li>
<li><a href="https://arxiv.org/abs/2006.11239">Denoising Diffusion Probabilistic Models</a></li>
<li><a href="https://arxiv.org/abs/2010.02502">Denoising Diffusion Implicit Models</a></li>
</ol></li>
</ul>
</div>
</div>
<hr>
<ul>
<li>Minimal PyTorch implementation accompanying these notes:
<ul>
<li><a href="https://github.com/riteshrm/nanoDiffusion">nanoDiffusion GitHub Repo</a></li>
</ul></li>
</ul>
<hr>
<section id="denoising-diffusion-probabilistic-models" class="level1">
<h1>Denoising Diffusion Probabilistic Models</h1>
<ul>
<li><p>Denoising Diffusion Probabilistic Models operate within a variational framework, much like VAEs</p></li>
<li><p>DDPMs introduce a clever twist that tackles some of the challenges faced by their predecessors</p></li>
<li><p>DDPMs involve two most distinct stochastic processes:-</p></li>
<li><p>The forward Pass (Fixed Encoder):</p>
<ul>
<li>Gradually corrupts data by injecting gaussian noise over multiple steps via a transition kernel <img src="https://latex.codecogs.com/png.latex?q(x_t%20%5Cmid%20x_%7Bt-1%7D)"></li>
<li>The data evolves into an isotropic gaussian distribution, effectively becoming pure noise</li>
<li>Encoder is fixed not learned.</li>
</ul></li>
</ul>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Tip
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>iso means same and tropic means direction. This is often represented as identity matrix which signifies that noise is uncorrelated across all dimensions.</li>
<li>pure noise means no identity of original data, only gaussian noise.</li>
</ul>
</div>
</div>
<ul>
<li>The reverse denoising process(Learnable Decoder):
<ul>
<li>A neural net learns to reverse the noise corruption through a parameterized distribution <img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_%7Bt-1%7D%7Cx_%7Bt%7D)"></li>
<li>Starting from pure noise, this process iteratively denoises to generate realistic samples</li>
<li>Each individual denoising step is a more manageable task than generating a complete sample from scratch as VAEs often attempt to do</li>
</ul></li>
</ul>
<section id="forward-process" class="level2">
<h2 class="anchored" data-anchor-id="forward-process">Forward Process</h2>
<ul>
<li>Forward process involves taking the noisy image from previous timestep and inject more noise</li>
<li><strong>Forward transition kernel:</strong> <img src="https://latex.codecogs.com/png.latex?q(x_%7Bt%7D%20%5Cmid%20x_%7Bt-1%7D)%20=%20N(x_%7Bt%7D,%20%5Csqrt%7B1-%5Cbeta_%7Bt%7D%7Dx_%7Bt-1%7D,%20%5Cbeta_%7Bt%7DI)"> where <img src="https://latex.codecogs.com/png.latex?x_%7Bt%7D"> is output, <img src="https://latex.codecogs.com/png.latex?%5Csqrt%7B1-%5Cbeta_%7Bt%7D%7Dx_%7Bt-1%7D"> is mean and <img src="https://latex.codecogs.com/png.latex?%5Cbeta_%7Bt%7DI"> is variance</li>
<li>Given <img src="https://latex.codecogs.com/png.latex?%5Cbeta_%7Bt%7D%20%5Csim%20(0,%201)">, In paper <img src="https://latex.codecogs.com/png.latex?%5Cbeta_%7Bstart%7D%20=%200.0001"> and <img src="https://latex.codecogs.com/png.latex?%5Cbeta_%7Bend%7D%20=%200.02"></li>
<li><img src="https://latex.codecogs.com/png.latex?q(x_%7B1%7D...x_%7BT%7D%20%5Cmid%20x_%7B0%7D):=%20%5Cprod_%7Bt=1%7D%5E%7BT%7D%20q(x_t%20%5Cmid%20x_%7Bt-1%7D)"></li>
<li><strong>Noise injection form:</strong> <img src="https://latex.codecogs.com/png.latex?x_%7Bt%7D%20=%20%5Csqrt%7B1-%5Cbeta_%7Bt%7D%7Dx_%7Bt-1%7D%20+%20%5Csqrt%5Cbeta_%7Bt%7D%20%5Cepsilon"></li>
<li>lets say <img src="https://latex.codecogs.com/png.latex?%5Calpha_%7Bt%7D%20=%201-%5Cbeta_%7Bt%7D"></li>
<li>Then <img src="https://latex.codecogs.com/png.latex?x_%7Bt%7D%20=%20%5Csqrt%5Calpha_%7Bt%7Dx_%7Bt-1%7D%20+%20%5Csqrt%7B1-%5Calpha_%7Bt%7D%7D%20%5Cepsilon"></li>
<li>Lets say <img src="https://latex.codecogs.com/png.latex?%5Cbar%7B%5Calpha%7D_%7Bt%7D:=%20%5Cprod_%7Bt=0%7D%5E%7BT%7D%20%5Calpha_t"></li>
</ul>
<table class="caption-top table">
<thead>
<tr class="header">
<th>Symbol</th>
<th>Meaning</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td><img src="https://latex.codecogs.com/png.latex?%5Cbeta_t"></td>
<td>noise schedule</td>
</tr>
<tr class="even">
<td><img src="https://latex.codecogs.com/png.latex?%5Calpha_t"></td>
<td><img src="https://latex.codecogs.com/png.latex?1-%5Cbeta_t"></td>
</tr>
<tr class="odd">
<td><img src="https://latex.codecogs.com/png.latex?%5Cbar%7B%5Calpha%7D_t"></td>
<td><img src="https://latex.codecogs.com/png.latex?%5Cprod_%7Bt=0%7D%5E%7BT%7D%20%5Calpha_t"></td>
</tr>
<tr class="even">
<td><img src="https://latex.codecogs.com/png.latex?%5Cepsilon"></td>
<td>gaussian noise</td>
</tr>
</tbody>
</table>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x_%7B1%7D%20=%20%5Csqrt%7B%5Calpha_%7B1%7D%7Dx_%7B0%7D%20+%20%5Csqrt%7B1-%5Calpha_%7B1%7D%7D%20%5Cepsilon"></li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7B2%7D%20=%20%5Csqrt%7B%5Calpha_%7B2%7D%7Dx_%7B1%7D%20+%20%5Csqrt%7B1-%5Calpha_%7B2%7D%7D%20%5Cepsilon"></li>
<li>if we substitute value of <img src="https://latex.codecogs.com/png.latex?x_%7B1%7D"> in above equation then</li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7B2%7D%20=%20%5Csqrt%7B%5Calpha_%7B2%7D%7D(%5Csqrt%5Calpha_%7B1%7Dx_%7B0%7D%20+%20%5Csqrt%7B1-%5Calpha_%7B1%7D%7D%20%5Cepsilon)%20+%20%5Csqrt%7B1-%5Calpha_%7B2%7D%7D%20%5Cepsilon"></li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7B2%7D%20=%20%5Csqrt%7B%5Calpha_%7B1%7D%5Calpha_%7B2%7D%7Dx_%7B0%7D%20+%20%5Csqrt%7B%5Calpha_%7B2%7D(1-%5Calpha_%7B1%7D)%7D%20%5Cepsilon%20+%20%5Csqrt%7B1-%5Calpha_%7B2%7D%7D%20%5Cepsilon"></li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7B2%7D%20=%20%5Csqrt%7B%5Calpha_%7B1%7D%5Calpha_%7B2%7D%7Dx_%7B0%7D%20+%20%5Csqrt%7B%5Calpha_%7B2%7D-%5Calpha_%7B1%7D%5Calpha_%7B2%7D%7D%20%5Cepsilon%20+%20%5Csqrt%7B1-%5Calpha_%7B2%7D%7D%20%5Cepsilon"></li>
</ul>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Tip
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>When we merge two normal distributions with different variance, the new distribution is as per below formula
<ul>
<li><img src="https://latex.codecogs.com/png.latex?N(0,%20%5Csigma_%7B1%7D%5E2I)%20+%20N(0,%20%5Csigma_%7B2%7D%5E2I)%20=%20N(0,%20(%5Csigma_%7B1%7D%5E2%20+%20%5Csigma_%7B2%7D%5E2)I)"></li>
</ul></li>
</ul>
</div>
</div>
<ul>
<li>Using above intuition we can change accordingly the forward equation</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Csqrt%7B%5Calpha_%7B2%7D-%5Calpha_%7B1%7D%5Calpha_%7B2%7D%7D%20%5Cepsilon%20+%20%5Csqrt%7B1-%5Calpha_%7B2%7D%7D%20%5Cepsilon%20=%20%5Csqrt%7B1-%5Calpha_%7B1%7D%5Calpha_%7B2%7D%7D%20%5Cepsilon"></li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7B2%7D%20=%20%5Csqrt%7B%5Calpha_%7B1%7D%5Calpha_%7B2%7D%7Dx_%7B0%7D%20+%20%5Csqrt%7B1-%5Calpha_%7B1%7D%5Calpha_%7B2%7D%7D%20%5Cepsilon"></li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7B2%7D%20=%20%5Csqrt%7B%5Cbar%7B%5Calpha%7D_%7B2%7D%7Dx_%7B0%7D%20+%20%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_%7B2%7D%7D%20%5Cepsilon"></li>
<li>If we generalize above equation it becomes</li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7Bt%7D%20=%20%5Csqrt%7B%5Cbar%7B%5Calpha%7D_%7Bt%7D%7Dx_%7B0%7D%20+%20%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_%7Bt%7D%7D%20%5Cepsilon"></li>
</ul>
</section>
<section id="reverse-process" class="level2">
<h2 class="anchored" data-anchor-id="reverse-process">Reverse Process</h2>
<section id="reverse-transition-parameterization" class="level3">
<h3 class="anchored" data-anchor-id="reverse-transition-parameterization">Reverse Transition (Parameterization)</h3>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?p(x_%7Bt-1%7D%7Cx_%7Bt%7D)%20=%20N(x_%7Bt-1%7D;%20%5Cmu_%7B%5Ctheta%7D(x_%7Bt%7D,%20t),%20%5Cepsilon_%7B%5Ctheta%7D(x_%7Bt%7D,%20t))"></li>
<li>Two neural networks to parameterize normal distribution <img src="https://latex.codecogs.com/png.latex?%5Cmu_%7B%5Ctheta%7D"> and <img src="https://latex.codecogs.com/png.latex?%5Cepsilon_%7B%5Ctheta%7D"></li>
<li>In paper variance is fixed so we only need to predict mean</li>
<li>We want to maximize the log likelihood of our data as we do in case of VAEs</li>
<li><img src="https://latex.codecogs.com/png.latex?log(p_%5Ctheta(x_%7B0%7D))"></li>
<li>but it is not easily computable as it depends on all the other <img src="https://latex.codecogs.com/png.latex?x_%7Bts%7D">:- <img src="https://latex.codecogs.com/png.latex?x_0,%20x_1,%20x_2..x_T"></li>
<li>So keeping track of other T-1 random variables is not possible as a solution we can compute ELBO as we did in VAEs</li>
</ul>
</section>
<section id="objective-log-likelihood-and-elbo" class="level3">
<h3 class="anchored" data-anchor-id="objective-log-likelihood-and-elbo">Objective: Log-Likelihood and ELBO</h3>
<ul>
<li><p>lets say when we have <img src="https://latex.codecogs.com/png.latex?f(x)"> and <img src="https://latex.codecogs.com/png.latex?g(x)"> and <img src="https://latex.codecogs.com/png.latex?f(x)"> &gt; <img src="https://latex.codecogs.com/png.latex?g(x)"> for all x then if we can maximize <img src="https://latex.codecogs.com/png.latex?g(x)"> then <img src="https://latex.codecogs.com/png.latex?f(x)"> will also be maximized</p></li>
<li><p>Using the above analogy, lets say <img src="https://latex.codecogs.com/png.latex?f(x)%20=%20log(p_%5Ctheta(x_%7B0%7D))"> and <img src="https://latex.codecogs.com/png.latex?g(x)%20=%20log(p_%5Ctheta(x_%7B0%7D))%20-%20D_%7BKL%7D(q(x_1:x_T%20%5Cmid%20x_0)%20%7C%7C%20p_%7B%5Ctheta%7D(x_1:x_T%20%5Cmid%20x_0))"></p></li>
<li><p>From above equations, we can see <img src="https://latex.codecogs.com/png.latex?f(x)"> and <img src="https://latex.codecogs.com/png.latex?g(x)"> are almost same, just there is one difference the KL-Divergence term which is being subtracted so if we are subtracting something then it is lesser than <img src="https://latex.codecogs.com/png.latex?f(x)"> and thus if we can somehow maximize <img src="https://latex.codecogs.com/png.latex?g(x)"> then we can maximize the likelihood of data samples</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?log(p_%5Ctheta(x_%7B0%7D))%20%3E=%20log(p_%5Ctheta(x_%7B0%7D)))%20-%20D_%7BKL%7D(q(x_1:x_T%20%5Cmid%20x_0)%20%7C%7C%20p_%7B%5Ctheta%7D(x_1:x_T%20%5Cmid%20x_0))"></p></li>
<li><p>Now we have to maximize <img src="https://latex.codecogs.com/png.latex?log(p_%5Ctheta(x_%7B0%7D)))%20-%20D_%7BKL%7D(q(x_1:x_T%20%5Cmid%20x_0)%20%7C%7C%20p_%7B%5Ctheta%7D(x_1:x_T%20%5Cmid%20x_0))"></p></li>
<li><p>Now our loss becomes negative of log likelihood <span id="eq-loss"><img src="https://latex.codecogs.com/png.latex?-log(p_%5Ctheta(x_%7B0%7D)))%20+%20D_%7BKL%7D(q(x_1:x_T%20%5Cmid%20x_0)%20%7C%7C%20p_%7B%5Ctheta%7D(x_1:x_T%20%5Cmid%20x_0))%20%5Ctag%7B1%7D"></span></p></li>
<li><p>Even now our loss still contains <img src="https://latex.codecogs.com/png.latex?p_%5Ctheta(x_%7B0%7D)"> and to eliminate that we have to make some changes to KL term</p></li>
</ul>
</section>
<section id="from-kl-term-to-vlb-step-by-step-expansion" class="level3">
<h3 class="anchored" data-anchor-id="from-kl-term-to-vlb-step-by-step-expansion">From KL Term to VLB (Step-by-step Expansion)</h3>
<ul>
<li>Now lets focus on KL-term only
<ul>
<li><img src="https://latex.codecogs.com/png.latex?D_%7BKL%7D(q(x_1:x_T%20%5Cmid%20x_0)%20%7C%7C%20p_%7B%5Ctheta%7D(x_1:x_T%20%5Cmid%20x_0))"> = <img src="https://latex.codecogs.com/png.latex?log%5Cfrac%7Bq(x_1:x_T%20%5Cmid%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_1:x_T%20%5Cmid%20x_0)%7D"></li>
<li>the denominator in the above expression can be replaced using bayes’ theorem</li>
<li><img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_1:x_T%20%5Cmid%20x_0)%20=%20%5Cfrac%7Bp_%7B%5Ctheta%7D(x_0%20%5Cmid%20x_1:x_T)p_%7B%5Ctheta%7D(x_1:x_T%20)%7D%7Bp_%7B%5Ctheta%7D(x_0)%7D"></li>
<li>Numerator can be replaced by <img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_0%20,%20x_1:x_T)"> using joint probability.</li>
<li>Now <img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_1:x_T%20%5Cmid%20x_0)%20=%20%5Cfrac%7Bp_%7B%5Ctheta%7D(x_0%20,%20x_1:x_T)%7D%7Bp_%7B%5Ctheta%7D(x_0)%7D"></li>
<li>where <img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_0%20,%20x_1:x_T)"> can be written as <img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_0:x_T)"> full joint distribution of entire diffusion trajectory</li>
<li>Now putting back the denominator value in KL term as <img src="https://latex.codecogs.com/png.latex?%5Cfrac%7Bp_%7B%5Ctheta%7D(x_0:x_T)%7D%7Bp_%7B%5Ctheta%7D(x_0)%7D"> gives us</li>
<li><img src="https://latex.codecogs.com/png.latex?log%5Cfrac%7Bq(x_1:x_T%20%5Cmid%20x_0)p_%7B%5Ctheta%7D(x_0)%7D%7Bp_%7B%5Ctheta%7D(x_0:x_T)%7D"></li>
<li>If we expand above equation as:-</li>
<li><img src="https://latex.codecogs.com/png.latex?log%5Cfrac%7Bq(x_1:x_T%20%5Cmid%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_0:x_T)%7D"> + <img src="https://latex.codecogs.com/png.latex?log(p_%7B%5Ctheta%7D(x_0))"></li>
</ul></li>
<li>lets add above derived kl term in Equation&nbsp;1 which gives</li>
<li><img src="https://latex.codecogs.com/png.latex?-log(p_%7B%5Ctheta%7D(x_%7B0%7D))%20+%20log%5Cfrac%7Bq(x_1:x_T%20%5Cmid%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_0:x_T)%7D%20+%20log(p_%7B%5Ctheta%7D(x_0))"></li>
<li>Notice <img src="https://latex.codecogs.com/png.latex?-log(p_%7B%5Ctheta%7D(x_%7B0%7D))"> gets cancelled with <img src="https://latex.codecogs.com/png.latex?log(p_%7B%5Ctheta%7D(x_0))"></li>
<li>Now our loss function becomes: <img src="https://latex.codecogs.com/png.latex?log%5Cfrac%7Bq(x_1:x_T%20%5Cmid%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_0:x_T)%7D"></li>
<li>Which gives <img src="https://latex.codecogs.com/png.latex?-log(p_%5Ctheta(x_%7B0%7D))%20%3C=%20log%5Cfrac%7Bq(x_1:x_T%20%5Cmid%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_0:x_T)%7D"> VLB</li>
</ul>
</section>
<section id="vlb-expansion-product-to-summation" class="level3">
<h3 class="anchored" data-anchor-id="vlb-expansion-product-to-summation">VLB Expansion (Product to Summation)</h3>
<ul>
<li>As we can see in VLB numerator is basically forward pass and denominator can be written as:</li>
<li><img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_%7B0:T%7D)%20=%20p(x_T)%5Cprod_%7Bt=1%7D%5E%7BT%7D%20p_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)"> and <img src="https://latex.codecogs.com/png.latex?p(x_T)"> is simply normal distribution with mean 0 and std 1</li>
<li>We can also write numerator as product of probabilities as <img src="https://latex.codecogs.com/png.latex?%5Cprod_%7Bt=1%7D%5E%7BT%7Dq(x_%7Bt%7D%20%5Cmid%20x_%7Bt-1%7D)"></li>
<li>Now our VLB becomes</li>
<li><img src="https://latex.codecogs.com/png.latex?log%5Cfrac%7B%5Cprod_%7Bt=1%7D%5E%7BT%7Dq(x_%7Bt%7D%20%5Cmid%20x_%7Bt-1%7D)%7D%7Bp(x_T)%5Cprod_%7Bt=1%7D%5E%7BT%7D%20p_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)%7D"></li>
<li>Now take out <img src="https://latex.codecogs.com/png.latex?p(x_T)"> which gives</li>
<li><img src="https://latex.codecogs.com/png.latex?-log(p(x_T))%20+%20log%5Cfrac%7B%5Cprod_%7Bt=1%7D%5E%7BT%7Dq(x_%7Bt%7D%20%5Cmid%20x_%7Bt-1%7D)%7D%7B%5Cprod_%7Bt=1%7D%5E%7BT%7D%20p_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)%7D"></li>
<li>Now we can transform product to summation which gives</li>
<li><img src="https://latex.codecogs.com/png.latex?-log(p(x_T))%20+%20%5Csum_%7Bt=1%7D%5E%7BT%7Dlog%5Cfrac%7Bq(x_%7Bt%7D%20%5Cmid%20x_%7Bt-1%7D)%7D%7Bp_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)%7D"></li>
<li>Now from summation one take out t=1 formulation and keep everything as it is which gives</li>
<li><img src="https://latex.codecogs.com/png.latex?-log(p(x_T))%20+%20%5Csum_%7Bt=2%7D%5E%7BT%7Dlog%5Cfrac%7Bq(x_%7Bt%7D%20%5Cmid%20x_%7Bt-1%7D)%7D%7Bp_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)%7D+%20log%5Cfrac%7Bq(x_1%20%5Cmid%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_0%20%5Cmid%20x_1)%7D"></li>
<li>now the numerator in summation of logs can be written as:</li>
<li><img src="https://latex.codecogs.com/png.latex?q(x_t%20%5Cmid%20x_%7Bt-1%7D)%20=%20%5Cfrac%7Bq(x_%7Bt-1%7D%20%5Cmid%20x_t)q(x_t)%7D%7Bq(x_%7Bt-1%7D)%7D"></li>
</ul>
</section>
<section id="conditioning-trick-reduce-variance-with-x_0" class="level3">
<h3 class="anchored" data-anchor-id="conditioning-trick-reduce-variance-with-x_0">Conditioning Trick: Reduce Variance with <img src="https://latex.codecogs.com/png.latex?x_0"></h3>
<ul>
<li><p>Now all the three terms 2 in numerator and 1 in denominator have really high variance, since we dont know what we started from that’s why author tried to reduce the variance by conditioning on x_0 and thus it reduces the choice of possible candidates. Intuitively given a noisy sample how can you say that what part do i have to remove, whereas if we also have x_0 then we might guess what part of noise to remove.</p></li>
<li><p>So <img src="https://latex.codecogs.com/png.latex?q(x_t%20%5Cmid%20x_%7Bt-1%7D)%20=%20%5Cfrac%7Bq(x_%7Bt-1%7D%20%5Cmid%20x_t,%20x_0)q(x_t%20%5Cmid%20x_0)%7D%7Bq(x_%7Bt-1%7D%20%5Cmid%20x_0)%7D"></p></li>
<li><p>Notice If we have not taken out the t=1 term then there have been a loop as</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?q(x_1%20%5Cmid%20x_0)%20=%20%5Cfrac%7Bq(x_0%20%5Cmid%20x_1)q(x_1)%7D%7Bq(x_0)%7D%20=%20%5Cfrac%7Bq(x_0%20%5Cmid%20x_1,%20x_0)q(x_1%20%5Cmid%20x_0)%7D%7Bq(x_0%20%5Cmid%20x_0)%7D"></p></li>
<li><p>lets put back the value of <img src="https://latex.codecogs.com/png.latex?q(x_t%20%5Cmid%20x_%7Bt-1%7D)"> back in original equation which gives</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?-log(p(x_T))%20+%20%5Csum_%7Bt=2%7D%5E%7BT%7Dlog(%5Cfrac%7Bq(x_%7Bt-1%7D%20%5Cmid%20x_%7Bt%7D,%20x_0)q(x_t%20%5Cmid%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)q(x_%7Bt-1%7D%20%5Cmid%20x_0)%7D)%20+%20log(%5Cfrac%7Bq(x_1%20%5Cmid%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_0%20%5Cmid%20x_1)%7D)"></p></li>
<li><p>lets expand summation one</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?-log(p(x_T))%20+%20%5Csum_%7Bt=2%7D%5E%7BT%7Dlog%5Cfrac%7Bq(x_%7Bt-1%7D%20%5Cmid%20x_%7Bt%7D,%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)%7D%20+%20%5Csum_%7Bt=2%7D%5E%7BT%7Dlog%5Cfrac%7Bq(x_t%20%5Cmid%20x_0)%7D%7Bq(x_%7Bt-1%7D%20%5Cmid%20x_0)%7D+%20log(%5Cfrac%7Bq(x_1%20%5Cmid%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_0%20%5Cmid%20x_1)%7D)"></p></li>
<li><p>the 3rd term in above equation if expanded is just <img src="https://latex.codecogs.com/png.latex?log%5Cfrac%7Bq(x_T%20%5Cmid%20x_0)%7D%7Bq(x_1%20%5Cmid%20x_0)%7D"></p></li>
<li><p>Now our loss looks like</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?-log(p(x_T))%20+%20%5Csum_%7Bt=2%7D%5E%7BT%7Dlog%5Cfrac%7Bq(x_%7Bt-1%7D%20%5Cmid%20x_%7Bt%7D,%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)%7D%20+%20log%5Cfrac%7Bq(x_T%20%5Cmid%20x_0)%7D%7Bq(x_1%20%5Cmid%20x_0)%7D+%20log(%5Cfrac%7Bq(x_1%20%5Cmid%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_0%20%5Cmid%20x_1)%7D)"></p></li>
<li><p>lets open up the 3rd and 4th term over log</p></li>
<li><p>$-log(p(x_T)) + <em>{t=2}^{T}log + log(q(x_T x_0)) - log(q(x_1 x_0)) + log(q(x_1 x_0)) - log(p</em>{}(x_0 x_1)) $</p></li>
<li><p>which gives us finally</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?log(%5Cfrac%7Bq(x_T%20%5Cmid%20x_0)%7D%7Bp(x_T)%7D)%20+%20%5Csum_%7Bt=2%7D%5E%7BT%7Dlog%5Cfrac%7Bq(x_%7Bt-1%7D%20%5Cmid%20x_%7Bt%7D,%20x_0)%7D%7Bp_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)%7D%20-%20log(p_%7B%5Ctheta%7D(x_0%20%5Cmid%20x_1))"></p></li>
</ul>
</section>
<section id="final-loss-decomposition-l_t-l_t-l_0" class="level3">
<h3 class="anchored" data-anchor-id="final-loss-decomposition-l_t-l_t-l_0">Final Loss Decomposition (<img src="https://latex.codecogs.com/png.latex?L_T">, <img src="https://latex.codecogs.com/png.latex?L_t">, <img src="https://latex.codecogs.com/png.latex?L_0">)</h3>
<ul>
<li>Let’s say
<ul>
<li><img src="https://latex.codecogs.com/png.latex?L_T%20=%20D_%7BKL%7D(q(x_T%20%5Cmid%20x_0)%20%7C%7C%20p(x_T))"></li>
<li><img src="https://latex.codecogs.com/png.latex?L_t%20=%20%5Csum_%7Bt=2%7D%5E%7BT%7DD_%7BKL%7D(q(x_%7Bt-1%7D%20%5Cmid%20x_t,%20x_0)%20%7C%7C%20p_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t))"></li>
<li><img src="https://latex.codecogs.com/png.latex?L_0%20=%20log(p_%7B%5Ctheta%7D(x_0%20%5Cmid%20x_1))"></li>
</ul></li>
<li>We can neglect <img src="https://latex.codecogs.com/png.latex?L_T"> since it does not involve any parameters</li>
<li>For <img src="https://latex.codecogs.com/png.latex?L_t"></li>
<li>Recall when we applied bayes’ rule, due to that both forward and reverse process are in same form now</li>
<li>Now lets focus on <img src="https://latex.codecogs.com/png.latex?L_t"> and <img src="https://latex.codecogs.com/png.latex?L_0"></li>
<li><img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)%20=%20N(x_%7Bt-1%7D;%20%5Cmu_%7B%5Ctheta%7D(x_t,%20t),%20%5Cepsilon_%7B%5Ctheta%7D(x_t,%20t))"></li>
<li>since <img src="https://latex.codecogs.com/png.latex?%5Cepsilon_%7B%5Ctheta%7D(x_t,%20t)"> is fixed which is <img src="https://latex.codecogs.com/png.latex?%5Cbeta_t%20I"></li>
<li><img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)%20=%20N(x_%7Bt-1%7D;%20%5Cmu_%7B%5Ctheta%7D(x_t,%20t),%20%5Cbeta_t%20I)"></li>
<li><img src="https://latex.codecogs.com/png.latex?q(x_%7Bt-1%7D%20%5Cmid%20x_t,%20x_0)"> also has a closed form solution which is equal to</li>
<li><img src="https://latex.codecogs.com/png.latex?N(x_%7Bt-1%7D;%20%5Ctilde%7B%5Cmu_t%7D(x_t,%20x_0),%20%5Ctilde%7B%5Cbeta_t%7DI)"></li>
<li>For derivation check out <a href="https://lilianweng.github.io/posts/2021-07-11-diffusion-models/">What are Diffusion Models?</a></li>
<li>But for now assume
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctilde%7B%5Cmu_t%7D(x_t,%20x_0)%20=%20%5Cfrac%7B%5Csqrt%7B%5Calpha_t%7D(1-%5Cbar%7B%5Calpha%7D_%7Bt-1%7D)%7D%7B1-%5Cbar%7B%5Calpha%7D_t%7DX_t%20+%20%5Cfrac%7B%5Csqrt%7B%5Cbar%7B%5Calpha%7D_%7Bt-1%7D%7D%5Cbeta_t%7D%7B1-%5Cbar%7B%5Calpha%7D_t%7DX_0"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctilde%7B%5Cbeta_t%7D%20=%20%5Cfrac%7B1-%5Cbar%7B%5Calpha%7D_%7Bt-1%7D%7D%7B1-%5Cbar%7B%5Calpha%7D_t%7D%5Cbeta_t"></li>
<li>Since _t is fixed, we can neglect this</li>
</ul></li>
</ul>
</section>
<section id="noise-prediction-reparameterization-predict-epsilon" class="level3">
<h3 class="anchored" data-anchor-id="noise-prediction-reparameterization-predict-epsilon">Noise Prediction Reparameterization (Predict epsilon)</h3>
<ul>
<li>from forward pass put the value of X_0 in <img src="https://latex.codecogs.com/png.latex?%5Ctilde%7B%5Cmu_t%7D"></li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7Bt%7D%20=%20%5Csqrt%7B%5Cbar%7B%5Calpha%7D_%7Bt%7D%7Dx_%7B0%7D%20+%20%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_%7Bt%7D%7D%20%5Cepsilon"></li>
<li>from above equation</li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7B0%7D%20=%20%5Cfrac%7Bx_%7Bt%7D%20-%20%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_%7Bt%7D%7D%20%5Cepsilon%7D%7B%5Csqrt%7B%5Cbar%7B%5Calpha%7D_%7Bt%7D%7D%7D"></li>
<li>which gives</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctilde%7B%5Cmu%7D(x_t,%20x_0)%20=%20%5Cfrac%7B1%7D%7B%5Csqrt%7B%5Calpha_t%7D%7D(x_t%20-%20%5Cfrac%7B%5Cbeta_t%7D%7B%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_t%7D%7D%5Cepsilon)"></li>
<li>Our model needs to predict <img src="https://latex.codecogs.com/png.latex?%5Ctilde%7B%5Cmu%7D(x_t,%20x_0)"></li>
<li>Since <img src="https://latex.codecogs.com/png.latex?x_t"> is available as input at training time, we can reparameterize the gaussian noise term instead to predict <img src="https://latex.codecogs.com/png.latex?%5Cepsilon"> from input <img src="https://latex.codecogs.com/png.latex?x_t"> at time step <img src="https://latex.codecogs.com/png.latex?t"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cmu_%7B%5Ctheta%7D(x_t,%20t)%20=%20%5Cfrac%7B1%7D%7B%5Csqrt%7B%5Calpha_t%7D%7D(x_t%20-%20%5Cfrac%7B%5Cbeta_t%7D%7B%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_t%7D%7D%5Cepsilon_%7B%5Ctheta%7D(x_t,%20t))"></li>
<li><img src="https://latex.codecogs.com/png.latex?L_t%20=%20%5Cfrac%7B1%7D%7B2%7B%5Csigma_%7Bt%7D%7D%5E2%7D%20MSE(%5Ctilde%7B%5Cmu_t%7D(x_t,%20x_0),%20%5Cmu_%7B%5Ctheta%7D(x_t,%20t))"></li>
<li>now comparing <img src="https://latex.codecogs.com/png.latex?%5Cmu_%7B%5Ctheta%7D(x_t,%20t)"> and <img src="https://latex.codecogs.com/png.latex?%5Ctilde%7B%5Cmu_t%7D(x_t,%20x_0)"></li>
<li><img src="https://latex.codecogs.com/png.latex?L_t%20=%20%5Cfrac%7B%7B%5Cbeta_%7Bt%7D%7D%5E2%7D%7B2%7B%5Csigma_%7Bt%7D%7D%5E2%5Calpha_t(1-%5Cbar%7B%5Calpha_t%7D)%7D%20MSE(%5Cepsilon,%20%5Cepsilon_%7B%5Ctheta%7D(x_t,%20t))"></li>
<li>Authors from the DDPM paper neglected the weighting term citing that it improves the sample quality and implementation is quite easy.</li>
<li>So <img src="https://latex.codecogs.com/png.latex?L_t%20=%20%20MSE(%5Cepsilon,%20%5Cepsilon_%7B%5Ctheta%7D(x_t,%20t))"></li>
<li>Now for <img src="https://latex.codecogs.com/png.latex?L_0"></li>
<li>Authors decided to neglect the last term but basically it was comparing with <img src="https://latex.codecogs.com/png.latex?x_0">, like how probable is the predicted <img src="https://latex.codecogs.com/png.latex?x_0"> given <img src="https://latex.codecogs.com/png.latex?x_1"></li>
<li>By neglecting <img src="https://latex.codecogs.com/png.latex?L_0">, while generating sample, we add noise till <img src="https://latex.codecogs.com/png.latex?t%3E1"> but at <img src="https://latex.codecogs.com/png.latex?t=1">, we just return the sample</li>
</ul>
</section>
<section id="sampling-step-x_t-1-from-x_t" class="level3">
<h3 class="anchored" data-anchor-id="sampling-step-x_t-1-from-x_t">Sampling Step (<img src="https://latex.codecogs.com/png.latex?x_%7Bt-1%7D"> from <img src="https://latex.codecogs.com/png.latex?x_t">)</h3>
<ul>
<li>Now back to starting sample generation</li>
<li><img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_t)%20=%20N(x_%7Bt-1%7D;%20%5Cmu_%7B%5Ctheta%7D(x_t,%20t),%20%5Cbeta_%7Bt%7DI)">, which gives</li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7Bt-1%7D%20=%20%5Cmu_%7B%5Ctheta%7D(x_t,%20t)%20+%20%5Csqrt%7B%5Cbeta_%7Bt%7D%7D%5Cepsilon"></li>
<li>now putting the value of <img src="https://latex.codecogs.com/png.latex?%5Cmu_%7B%5Ctheta%7D(x_t,%20t)"> gives</li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7Bt-1%7D%20=%20%5Cfrac%7B1%7D%7B%5Csqrt%7B%5Calpha_%7Bt%7D%7D%7D(x_t%20-%20%5Cfrac%7B%5Cbeta_t%7D%7B%5Csqrt(1-%5Cbar%7B%5Calpha%7D_t)%7D%5Cepsilon_%7B%5Ctheta%7D(x_t,%20t))%20+%20%5Csqrt%7B%5Cbeta_%7Bt%7D%7D%5Cepsilon"></li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/diffusion-models/train.png" style="width:80%" class="figure-img">
<figcaption>
Training Algorithm
</figcaption>
</figure>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/diffusion-models/sample.png" style="width:80%" class="figure-img">
<figcaption>
Sampling Algorithm
</figcaption>
</figure>
</section>
</section>
<section id="implementation" class="level2">
<h2 class="anchored" data-anchor-id="implementation">Implementation</h2>
<ul>
<li>Below is simple implementation of forward process, reverse process, sampling and loss, where eps_theta is our denoiser model</li>
<li>For the complete class-conditioned DDPM implementation, check out:- <a href="https://github.com/riteshrm/nanoDiffusion/ddpm.py">nanoDiffusion/ddpm.py</a></li>
</ul>
<div id="ddpm-reference-implementation" class="cell" data-execution_count="1">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb1" style="background: #f1f3f5;"><pre class="sourceCode numberSource python number-lines code-with-copy"><code class="sourceCode python"><span id="cb1-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb1-2"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> Diffusion():</span>
<span id="cb1-3">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, beta_start, beta_end, timesteps):</span>
<span id="cb1-4">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_start <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> beta_start</span>
<span id="cb1-5">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_end <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> beta_end</span>
<span id="cb1-6">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.timesteps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> timesteps</span>
<span id="cb1-7">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.linspace(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_start, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_end, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.timesteps)</span>
<span id="cb1-8">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alpha_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_t</span>
<span id="cb1-9">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alphabar_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.cumprod(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alpha_t, dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>)</span>
<span id="cb1-10">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps_theta <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.nn.Module()</span>
<span id="cb1-11"></span>
<span id="cb1-12">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> forward_process(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_0, eps, t):</span>
<span id="cb1-13">        alphabar_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alphabar_t[t].view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb1-14">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.sqrt(alphabar_t)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>x_0 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> torch.sqrt(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> alphabar_t)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>eps</span>
<span id="cb1-15">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t</span>
<span id="cb1-16">    </span>
<span id="cb1-17">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> reverse_process(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_t, t, eps<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>):</span>
<span id="cb1-18">        pred_eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps_theta(x_t, t)</span>
<span id="cb1-19">        alphabar_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alphabar_t[t].view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb1-20">        alpha_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alpha_t[t].view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb1-21">        beta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_t[t].view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb1-22">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> eps <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>:</span>
<span id="cb1-23">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> (<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>torch.sqrt(alpha_t))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>(x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> (beta_t<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>torch.sqrt(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> alphabar_t))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>pred_eps)</span>
<span id="cb1-24">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span>:</span>
<span id="cb1-25">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> (<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>torch.sqrt(alpha_t))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>(x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> (beta_t<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>torch.sqrt(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> alphabar_t))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>pred_eps) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> torch.sqrt(beta_t)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>eps</span>
<span id="cb1-26">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_prevt</span>
<span id="cb1-27">    </span>
<span id="cb1-28">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sample(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, shape):</span>
<span id="cb1-29">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(shape)</span>
<span id="cb1-30">        </span>
<span id="cb1-31">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> t <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.timesteps<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>):</span>
<span id="cb1-32">            <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> t<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">==</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>:</span>
<span id="cb1-33">                x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.reverse_process(x_t, t)</span>
<span id="cb1-34">            <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span>:</span>
<span id="cb1-35">                eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(shape)</span>
<span id="cb1-36">                x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.reverse_process(x_t, t, eps)</span>
<span id="cb1-37">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t</span>
<span id="cb1-38">    </span>
<span id="cb1-39">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> loss(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_0):</span>
<span id="cb1-40">        t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randint(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.timesteps, (x_0.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>],))</span>
<span id="cb1-41">        eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn_like(x_0)</span>
<span id="cb1-42">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.forward_process(x_0, eps, t)</span>
<span id="cb1-43">        pred_eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps_theta(x_t, t)</span>
<span id="cb1-44">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> torch.nn.functional.mse_loss(eps, pred_eps)</span></code></pre></div></div>
</div>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/diffusion-models/ddpm.gif" style="width:60%" class="figure-img">
<figcaption>
DDPM samples from epoch 0 through training
</figcaption>
</figure>
<hr>
</section>
</section>
<section id="faster-sampling-denoising-diffusion-implicit-models" class="level1">
<h1>Faster Sampling (Denoising Diffusion Implicit Models)</h1>
<section id="motivation-fewer-steps-than-ddpm" class="level2">
<h2 class="anchored" data-anchor-id="motivation-fewer-steps-than-ddpm">Motivation: Fewer Steps than DDPM</h2>
<ul>
<li>So DDPM is taking the same number of steps as in forward process to generate a sample.</li>
<li>May be we can make larger jumps in reverse process, but the resultants are not good due to stochastic nature in DDPM reverse</li>
<li>DDIM aims to follow a non-markovian process, which also keeps the marginal same as DDPM at the same avoiding stochasticity in reverse process</li>
<li>Basically DDIM proposes q [<img src="https://latex.codecogs.com/png.latex?q_%7B%5Csigma%7D(x_%7Bt-1%7D%20%5Cmid%20x_t,%20x_0)">] such that
<ul>
<li>Marginal is same as DDPM :- <img src="https://latex.codecogs.com/png.latex?q_%7B%5Csigma%7D(x_%7Bt%7D%20%5Cmid%20x_0)%20=%20q(x_%7Bt%7D%20%5Cmid%20x_0)"></li>
<li>Generation process can be made deterministic:- <img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_1)"> can be made deterministic</li>
</ul></li>
</ul>
</section>
<section id="ddim-setup-non-markovian-same-marginals" class="level2">
<h2 class="anchored" data-anchor-id="ddim-setup-non-markovian-same-marginals">DDIM Setup: Non-Markovian, Same Marginals</h2>
<ul>
<li>Which gives</li>
<li><img src="https://latex.codecogs.com/png.latex?q_%7B%5Csigma%7D(x_%7Bt-1%7D%20%5Cmid%20x_t,%20x_0)%20=%20N(%5Csqrt%7B%5Cbar%7B%5Calpha%7D_%7Bt-1%7D%7Dx_0%20+%20%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_%7Bt-1%7D-%5Csigma_t%5E2%7D%5Cfrac%7Bx_t%20-%20%5Csqrt%7B%5Cbar%7B%5Calpha%7D_t%7Dx_0%7D%7B%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_1%7D%7D,%20%5Csigma_t%5E2I)"></li>
</ul>
</section>
<section id="deterministic-sampling-sigma-0" class="level2">
<h2 class="anchored" data-anchor-id="deterministic-sampling-sigma-0">Deterministic Sampling (sigma = 0)</h2>
<ul>
<li>After setting <img src="https://latex.codecogs.com/png.latex?%5Csigma%20=%200">, there will not be any stochasticity</li>
<li><img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x_%7Bt-1%7D%20%5Cmid%20x_1)%20%20%5Ctriangleq%20q_%7B%5Csigma=0%7D(x_%7Bt-1%7D%20%5Cmid%20x_t,%20%5Chat%7Bx_0%7D(t))"></li>
<li>where <img src="https://latex.codecogs.com/png.latex?%5Chat%7Bx_0%7D(t)"> is approximated <img src="https://latex.codecogs.com/png.latex?%5Chat%7Bx_0%7D"> at every step</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Chat%7Bx_0%7D(t)%20=%20%5Cfrac%7Bx_t%20-%20%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_t%7D%5Cepsilon_%7B%5Ctheta%7D(x_t,%20t)%7D%7B%5Csqrt%7B%5Cbar%7B%5Calpha%7D_t%7D%7D"></li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7Bt-1%7D%20=%20%5Csqrt%7B%5Cbar%7B%5Calpha%7D_%7Bt-1%7D%7D%5Chat%7Bx_0%7D(t)%20+%20%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_%7Bt-1%7D%7D%5Cepsilon_%7B%5Ctheta%7D(x_t,%20t)%20+%200"></li>
<li>Our prediction of the clean image from time t that we noise to time t-1 with no stochasticity</li>
</ul>
</section>
<section id="update-rule-x_tau_i-1-from-x_tau_i" class="level2">
<h2 class="anchored" data-anchor-id="update-rule-x_tau_i-1-from-x_tau_i">Update Rule (<img src="https://latex.codecogs.com/png.latex?x_%7B%5Ctau_%7Bi-1%7D%7D"> from <img src="https://latex.codecogs.com/png.latex?x_%7B%5Ctau_i%7D">)</h2>
<ul>
<li>Lets generalize it</li>
<li><img src="https://latex.codecogs.com/png.latex?x_%7B%5Ctau_%7Bi-1%7D%7D%20=%20%5Csqrt%7B%5Cbar%7B%5Calpha%7D_%7B%5Ctau_%7Bi-1%7D%7D%7D%5Chat%7Bx_0%7D(%7B%5Ctau_%7Bi%7D%7D)%20+%20%5Csqrt%7B1-%5Cbar%7B%5Calpha%7D_%7B%5Ctau_%7Bi-1%7D%7D%7D%5Cepsilon_%7B%5Ctheta%7D(x_%7B%5Ctau_%7Bi%7D%7D,%20%5Ctau_%7Bi%7D)"></li>
</ul>
</section>
<section id="implementation-1" class="level2">
<h2 class="anchored" data-anchor-id="implementation-1">Implementation</h2>
<ul>
<li>For the complete class-conditioned DDIM implementation, check out:- <a href="https://github.com/riteshrm/nanoDiffusion/ddim.py">nanoDiffusion/ddim.py</a></li>
</ul>
<div id="ddim-reference-implementation" class="cell" data-execution_count="2">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb2" style="background: #f1f3f5;"><pre class="sourceCode numberSource python number-lines code-with-copy"><code class="sourceCode python"><span id="cb2-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb2-2"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> Diffusion():</span>
<span id="cb2-3">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, beta_start, beta_end, timesteps):</span>
<span id="cb2-4">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_start <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> beta_start</span>
<span id="cb2-5">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_end <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> beta_end</span>
<span id="cb2-6">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.timesteps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> timesteps</span>
<span id="cb2-7">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.linspace(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_start, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_end, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.timesteps)</span>
<span id="cb2-8">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alpha_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_t</span>
<span id="cb2-9">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alphabar_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.cumprod(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alpha_t, dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>)</span>
<span id="cb2-10">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps_theta <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.nn.Module()</span>
<span id="cb2-11"></span>
<span id="cb2-12">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> forward_process(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_0, eps, t):</span>
<span id="cb2-13">        alphabar_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alphabar_t[t].view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb2-14">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.sqrt(alphabar_t)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>x_0 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> torch.sqrt(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> alphabar_t)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>eps</span>
<span id="cb2-15">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_t</span>
<span id="cb2-16">    </span>
<span id="cb2-17">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> reverse_process(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_t, t, eps<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>):</span>
<span id="cb2-18">        pred_eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps_theta(x_t, t)</span>
<span id="cb2-19">        alphabar_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alphabar_t[t].view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb2-20">        alpha_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alpha_t[t].view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb2-21">        beta_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.beta_t[t].view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb2-22">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> eps <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>:</span>
<span id="cb2-23">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> (<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>torch.sqrt(alpha_t))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>(x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> (beta_t<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>torch.sqrt(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> alphabar_t))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>pred_eps)</span>
<span id="cb2-24">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span>:</span>
<span id="cb2-25">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> (<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>torch.sqrt(alpha_t))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>(x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> (beta_t<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>torch.sqrt(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> alphabar_t))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>pred_eps) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> torch.sqrt(beta_t)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>eps</span>
<span id="cb2-26">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_prevt</span>
<span id="cb2-27">    </span>
<span id="cb2-28">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sample_ddim(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, shape, num_steps):</span>
<span id="cb2-29">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(shape)</span>
<span id="cb2-30"></span>
<span id="cb2-31">        steps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.linspace(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.timesteps<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>, num_steps, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">int</span>)</span>
<span id="cb2-32"></span>
<span id="cb2-33">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(num_steps):</span>
<span id="cb2-34">            t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> steps[i]</span>
<span id="cb2-35">            alphabar_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alphabar_t[t].view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb2-36">            pred_eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps_theta(x_t, t)</span>
<span id="cb2-37">            x_hat <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> (x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> (<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>alphabar_t).sqrt()<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>pred_eps)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>alphabar_t.sqrt()</span>
<span id="cb2-38">            <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> i <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">==</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">len</span>(steps)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>:</span>
<span id="cb2-39">                <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x_hat</span>
<span id="cb2-40">            prev_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> steps[i<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>]</span>
<span id="cb2-41">            alphabar_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.alphabar_t[prev_t].view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb2-42">            x_prevt <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> alphabar_prevt.sqrt()<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>x_hat <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> (<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>alphabar_prevt).sqrt()<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>pred_eps</span>
<span id="cb2-43">            x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x_prevt</span>
<span id="cb2-44">    </span>
<span id="cb2-45">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> loss(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x_0):</span>
<span id="cb2-46">        t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randint(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.timesteps, (x_0.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>],))</span>
<span id="cb2-47">        eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn_like(x_0)</span>
<span id="cb2-48">        x_t <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.forward_process(x_0, eps, t)</span>
<span id="cb2-49">        pred_eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.eps_theta(x_t, t)</span>
<span id="cb2-50">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> torch.nn.functional.mse_loss(eps, pred_eps)</span></code></pre></div></div>
</div>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/diffusion-models/ddim.gif" style="width:60%" class="figure-img">
<figcaption>
DDIM samples from epoch 0 through training
</figcaption>
</figure>


</section>
</section>

 ]]></description>
  <category>Generative AI</category>
  <guid>https://riteshrm.github.io/posts/diffusion-models/</guid>
  <pubDate>Mon, 18 May 2026 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/diffusion-models/diffusion_model.png" medium="image" type="image/png" height="96" width="144"/>
</item>
<item>
  <title>Variational Autoencoder</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/variational-autoencoder/</link>
  <description><![CDATA[ 





<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Tip</span>References
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>This is mostly based on:
<ol type="1">
<li><a href="https://www.youtube.com/watch?v=1RPdu_5FCfk">Understanding Variational Autoencoder</a></li>
<li><a href="https://www.youtube.com/watch?v=iwEzwTTalbg">Variational Autoencoder - Model, ELBO, loss function and maths explained easily</a></li>
</ol></li>
</ul>
</div>
</div>
<hr>
<ul>
<li>Minimal PyTorch implementation accompanying these notes:
<ul>
<li><a href="https://github.com/riteshrm/vae">vae GitHub Repo</a></li>
</ul></li>
</ul>
<hr>
<section id="autoencoders" class="level1">
<h1>Autoencoders</h1>
<ul>
<li>They are used for:-
<ul>
<li>converting higher dimension to lower dimension</li>
<li>Representation Learning</li>
</ul></li>
</ul>
<section id="cons-of-autoencoders" class="level2">
<h2 class="anchored" data-anchor-id="cons-of-autoencoders">Cons of Autoencoders</h2>
<ul>
<li>The encoded values can be used as representation but deep down they don’t have any meaningful information.</li>
<li>There is no semantic relationship between encoded data points like zebra or cat or tomato. They will be encoded but there will not be any similarity.</li>
<li>Since everything is being encoded to the points, not distribution, we can not sample any new data point</li>
</ul>
<hr>
</section>
</section>
<section id="what-we-actually-want" class="level1">
<h1>What We Actually Want?</h1>
<ul>
<li>Instead of encoding to data points, encode into some distribution so that we can generate new data points.</li>
<li>But even if we try to encode to a distribution, the model will again try to memorise things as it just have to minimize the reconstruction loss.</li>
<li>Get variations in reconstructed images.</li>
<li>So we want is that:
<ul>
<li>There should be some sort of latent distribution which is just not encoded to points, it should be wide enough to capture entire latent space so that we can have higher variance and thus variation in reconstructed images.</li>
<li>And also distributions should not be far apart from each other so that if we sample any latent then it should give us something meaningful not random images.</li>
</ul></li>
</ul>
<hr>
</section>
<section id="how-do-we-achieve-above-requirements" class="level1">
<h1>How Do We Achieve Above Requirements?</h1>
<ul>
<li>Gaussian distribution would help in achieving above objectives
<ul>
<li>It will try to have <strong>mean as close to zero</strong> as possible thus keep distributions closer to each other.</li>
<li>It will try to have <strong>unit variance</strong> thus ensuring that distributions have higher variance and hence disable the network to collapse distributions to a point.</li>
</ul></li>
<li>So basically what we want is that our <strong>encoded distribution</strong> should look like a <strong>Gaussian distribution</strong>.</li>
<li>We can use some sort of metric that will help in keeping the <strong>encoded distribution</strong> and <strong>Gaussian distribution</strong> as similar as possible.</li>
<li>And that metric is <strong>KL-Divergence</strong>, which we can use to do so.</li>
</ul>
<hr>
</section>
<section id="before-moving-forward-some-prerequisites" class="level1">
<h1>Before Moving Forward Some Prerequisites</h1>
<section id="probability-vs-likelihood" class="level2">
<h2 class="anchored" data-anchor-id="probability-vs-likelihood">Probability vs Likelihood</h2>
<ul>
<li>You can check out <a href="https://www.youtube.com/watch?v=pYxNSUDSFH4">In Statistics, Probability is not Likelihood</a> for the same.</li>
<li>Consider the weights of mice</li>
</ul>
<section id="probability" class="level3">
<h3 class="anchored" data-anchor-id="probability">Probability</h3>
<ul>
<li>Let’s say we have plotted all the weights which gives us mean 32 and std 2.5, now what is the probability of having a mouse which has weight between 32-34 is given by area under the curve</li>
<li><img src="https://latex.codecogs.com/png.latex?P(weight%20b/w%2032-34%20%7C%20mean=32,%20std=2.5)"></li>
</ul>
</section>
<section id="likelihood" class="level3">
<h3 class="anchored" data-anchor-id="likelihood">Likelihood</h3>
<ul>
<li><p>Considering we have fixed data/samples what is the likelihood of the current mean and std, which is given by the value corresponding to given weight on Y-axis.</p></li>
<li><p>Basically in this case we will have a continuous distribution with mean as 32 and std as 2.5 and then we will found out what is the likelihood of having 34 as weight.</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?L(mean=32,%20std=2.5%20%7C%20weight=34)"></p></li>
<li><p>While training we try to maximize the likelihood for our data points so that our model can represent the data samples as closely as possible</p></li>
<li><p>During inference, we check the probability of given sample based on the params(mean and std) we have learned while maximizing the likelihood.</p></li>
</ul>
</section>
</section>
<section id="some-maths" class="level2">
<h2 class="anchored" data-anchor-id="some-maths">Some Maths</h2>
<ul>
<li><p>The expectation <img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D%5Bx%5D%20=%20%5Cint%20x%20%5C,%20p(x)%20%5C,%20dx"> gives the mean. where <img src="https://latex.codecogs.com/png.latex?x"> is value and <img src="https://latex.codecogs.com/png.latex?p(x)"> is probability density and <img src="https://latex.codecogs.com/png.latex?dx"> is tiny interval.</p></li>
<li><p>Simply we can say that it is long run average for continuous random variable x where x∼p(x).</p></li>
<li><p>Similarly <img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D%5Bf(x)%5D%20=%20%5Cint%20f(x)%20%5C,%20p(x)%20%5C,%20dx"></p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?f(x)%20=%20x%5E2"> then <img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D%5Bx%5E2%5D%20=%20%5Cint%20x%5E2%20%5C,%20p(x)%20%5C,%20dx"></li>
</ul></li>
<li><p>Similarly for discrete one is:</p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D%5BX%5D%20=%20%5Csum_%7Bx%7D%20x%20%5C,%20p(x)">, where <img src="https://latex.codecogs.com/png.latex?x"> is value and <img src="https://latex.codecogs.com/png.latex?p(x)"> is probability.</li>
</ul></li>
<li><p>Chain rule of probability <img src="https://latex.codecogs.com/png.latex?p(x,%20y)%20=%20p(x%7Cy)p(y)%20=%20p(y%7Cx)p(x)"></p></li>
<li><p>Bayes’ Theorem</p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?P(x%20%5Cmid%20y)%20=%20%5Cfrac%7BP(y%20%5Cmid%20x)%20%5C,%20P(x)%7D%7BP(y)%7D"></li>
</ul></li>
<li><p>Kullback Leibler Divergence</p>
<ul>
<li>It allows to measure the distance between two probability distributions.</li>
<li><img src="https://latex.codecogs.com/png.latex?D_%7B%5Ctext%7BKL%7D%7D(P%20%5C%7C%20Q)%20=%20%5Cint_%7B-%5Cinfty%7D%5E%7B%5Cinfty%7D%20p(x)%20%5Clog%20%5Cfrac%7Bp(x)%7D%7Bq(x)%7D%20%5C,%20dx"></li>
<li>Properties:-
<ul>
<li>Not symmetric i.e.&nbsp;$D_{}(P | Q) D_{}(Q | P) $</li>
<li><img src="https://latex.codecogs.com/png.latex?D_%7B%5Ctext%7BKL%7D%7D(P%20%5C%7C%20Q)%20%5Cgeq%200"></li>
<li><img src="https://latex.codecogs.com/png.latex?D_%7B%5Ctext%7BKL%7D%7D(P%20%5C%7C%20Q)%20=%200"> if <img src="https://latex.codecogs.com/png.latex?P=Q"></li>
</ul></li>
</ul></li>
</ul>
</section>
<section id="monte-carlo-estimation" class="level2">
<h2 class="anchored" data-anchor-id="monte-carlo-estimation">Monte Carlo Estimation</h2>
<ul>
<li>It is a way to approximately compute expected value.</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D_%7Bx%20%5Csim%20p%7D%5Bg(x)%5D%20=%20%5Csum_%7Bx%7D%20g(x)%20%5C,%20p(x)"></li>
<li>To get approximate expected value
<ul>
<li>Sample T IID(Independent and Identically Distributed) samples from P</li>
<li>estimate expected value as:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Chat%7Bg%7D(x_%7B1%7D....x_%7BT%7D)%20%5Ctriangleq%20%5Cfrac%7B1%7D%7BT%7D%5Csum_%7Bt=1%7D%5E%7BT%7D%20g(x_%7Bt%7D)"></li>
</ul></li>
</ul></li>
</ul>
</section>
<section id="monte-carlo-gradient-estimation" class="level2">
<h2 class="anchored" data-anchor-id="monte-carlo-gradient-estimation">Monte Carlo Gradient Estimation</h2>
<ul>
<li>Similarly it is a way to estimate gradients when the objective contains an expectation over random variables.</li>
</ul>
<hr>
</section>
</section>
<section id="lets-define-our-model" class="level1">
<h1>Let’s Define Our Model</h1>
<section id="likelihood-as-marginalization" class="level2">
<h2 class="anchored" data-anchor-id="likelihood-as-marginalization">Likelihood as Marginalization</h2>
<ul>
<li>We can define the likelihood of our data as the marginalization over the joint probability with respect to the latent variable
<ul>
<li><img src="https://latex.codecogs.com/png.latex?p(x)%20=%20%5Cint%20p(x,%20z)%20dz%20=%20%5Cint%20p(x%7Cz)p(z)dz"></li>
<li>Now what does above line means
<ul>
<li>Consider we have only a single image and there are 3 latent codes which might have produced x then</li>
<li><img src="https://latex.codecogs.com/png.latex?p(x)%20=%20p(x%7Cz_1)p(z_1)%20+%20p(x%7Cz_2)p(z_2)%20+%20p(x%7Cz_3)p(z_3)"></li>
<li>Using chain rule we can write above equation as</li>
<li><img src="https://latex.codecogs.com/png.latex?p(x)%20=%20p(x,%20z_1)%20+%20p(x,%20z_2)%20+%20p(x,%20z_3)"></li>
<li>So what if we have infinitely many z, so above formula to incorporate all z</li>
</ul></li>
</ul></li>
</ul>
</section>
<section id="why-it-is-intractable" class="level2">
<h2 class="anchored" data-anchor-id="why-it-is-intractable">Why It Is Intractable</h2>
<ul>
<li><p>But it is intractable because we would need to evaluate this integral over all latent variables <img src="https://latex.codecogs.com/png.latex?z"> because it is of very high dimension.</p></li>
<li><p>Intractable Problem:- A problem that can be solved in theory (e.g.&nbsp;given large but finite resources, especially time), but for which in practice any solution takes too many resources to be useful is known as intractable problem.</p>
<ul>
<li>Like guessing the wi-fi password of your neighbour. In theory you can generate all the possible combinations but it will take years.</li>
</ul></li>
<li><p>In theory it is possible but practically it is not or we can use the chain rule of probability</p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?p(x)%20=%20%5Cfrac%7Bp(x,%20z)%7D%7Bp(z%7Cx)%7D"></li>
</ul></li>
<li><p>We don’t have ground truth <img src="https://latex.codecogs.com/png.latex?p(z%7Cx)"> which is also what we are trying to find.</p></li>
<li><p>Now it seems like chicken and egg problem like which came first</p></li>
<li><p>We want to calculate <img src="https://latex.codecogs.com/png.latex?p(x)"> which depends on <img src="https://latex.codecogs.com/png.latex?p(z%7Cx)"> and <img src="https://latex.codecogs.com/png.latex?p(z%7Cx)"> depends on <img src="https://latex.codecogs.com/png.latex?p(x)"></p></li>
</ul>
</section>
<section id="approximate-posterior" class="level2">
<h2 class="anchored" data-anchor-id="approximate-posterior">Approximate Posterior</h2>
<ul>
<li>Usually, when we can’t find something we try to approximate it
<ul>
<li><img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(z%7Cx)%20%5Capprox%20q_%7B%5Cphi%7D(z%7Cx)"></li>
<li>Where <img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(z%7Cx)"> is our true posterior(because we already assumed that <img src="https://latex.codecogs.com/png.latex?z"> is from Normal distribution so <img src="https://latex.codecogs.com/png.latex?p(z)"> is prior, and now given image x our assumption about z has changed for example if image was of face then now z might have some dimensions activated for face) parameterized by <img src="https://latex.codecogs.com/png.latex?%5Ctheta"> that we can’t evaluate due to its intractability and <img src="https://latex.codecogs.com/png.latex?q_%7B%5Cphi%7D(z%7Cx)"> is an approximate posterior parameterized by <img src="https://latex.codecogs.com/png.latex?%5Cphi"></li>
</ul></li>
</ul>
</section>
<section id="lets-do-some-maths" class="level2">
<h2 class="anchored" data-anchor-id="lets-do-some-maths">Let’s Do Some Maths</h2>
<section id="introducing-q_phizx" class="level3">
<h3 class="anchored" data-anchor-id="introducing-q_phizx">Introducing <img src="https://latex.codecogs.com/png.latex?q_%7B%5Cphi%7D(z%7Cx)"></h3>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%7B%5Clog%7Dp_%7B%5Ctheta%7D(x)%20=%20%7B%5Clog%7Dp_%7B%5Ctheta%7D(x)"></li>
<li><img src="https://latex.codecogs.com/png.latex?=%20%7B%5Clog%7Dp_%7B%5Ctheta%7D(x)"> x 1 Multiply by 1</li>
<li><img src="https://latex.codecogs.com/png.latex?=%20%7B%5Clog%7Dp_%7B%5Ctheta%7D(x)%20%5Cint%20q_%7B%5Cphi%7D(z%7Cx)%20dz">. Since <img src="https://latex.codecogs.com/png.latex?%5Cint%20q_%7B%5Cphi%7D(z%7Cx)%20dz%20=%201">. because summation of all the z that could have produced x is 1, which is what we are trying to calculate. You can take analogy of discrete example also <img src="https://latex.codecogs.com/png.latex?p(z_1%7Cx)%20+%20p(z_2%7Cx)%20=%201"> if we consider only z which could have produced x.</li>
<li><img src="https://latex.codecogs.com/png.latex?=%20%7B%5Cint%5Clog%7Dp_%7B%5Ctheta%7D(x)%20%20q_%7B%5Cphi%7D(z%7Cx)%20dz"> bring <img src="https://latex.codecogs.com/png.latex?%7B%5Clog%7Dp_%7B%5Ctheta%7D(x)"> inside integral since it does not depend on z and can be treated as constant.</li>
<li><img src="https://latex.codecogs.com/png.latex?=%20%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7Dp_%7B%5Ctheta%7D(x)%5D">
<ul>
<li>basically above term is equal to <img src="https://latex.codecogs.com/png.latex?%7B%5Clog%7Dp_%7B%5Ctheta%7D(x)"> but we want to somehow introduce z because <img src="https://latex.codecogs.com/png.latex?%7B%5Clog%7Dp_%7B%5Ctheta%7D(x)"> is independent of z and using <img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D%5Bx%5D%20=%20%5Cint%20constant%20%5C,%20p(x)%20%5C,%20dx"> is constant because we can take constant outside and the remaining integral will give 1.</li>
</ul></li>
<li><img src="https://latex.codecogs.com/png.latex?=%20%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)%7D%7Bp_%7B%5Ctheta%7D(z%7Cx)%7D%5D"> Apply the equation <img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x)%20=%20%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)%7D%7Bp_%7B%5Ctheta%7D(z%7Cx)%7D"></li>
<li><img src="https://latex.codecogs.com/png.latex?=%20%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)q_%7B%5Cphi%7D(z%7Cx)%7D%7Bp_%7B%5Ctheta%7D(z%7Cx)q_%7B%5Cphi%7D(z%7Cx)%7D%5D"> Multiply by 1</li>
<li><img src="https://latex.codecogs.com/png.latex?=%20%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)%7D%7Bq_%7B%5Cphi%7D(z%7Cx)%7D%5D%20+%20%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7D%5Cfrac%7Bq_%7B%5Cphi%7D(z%7Cx)%7D%7Bp_%7B%5Ctheta%7D(z%7Cx)%7D%5D"> Split the expectation</li>
<li><img src="https://latex.codecogs.com/png.latex?=%20%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)%7D%7Bq_%7B%5Cphi%7D(z%7Cx)%7D%5D%20+%20D_%7B%5Ctext%7BKL%7D%7D(q_%7B%5Cphi%7D(z%7Cx)%20%5C%7C%20p_%7B%5Ctheta%7D(z%7Cx))"> By definition of KL Divergence</li>
<li><img src="https://latex.codecogs.com/png.latex?%7B%5Clog%7Dp_%7B%5Ctheta%7D(x)%20=%20ELBO%20+%20D_%7B%5Ctext%7BKL%7D%7D(q_%7B%5Cphi%7D(z%7Cx)%20%5C%7C%20p_%7B%5Ctheta%7D(z%7Cx))"> where <strong>ELBO</strong> is evidence lower bound and second term is KL divergence since it will always be greater than 0</li>
<li>Since we are trying to maximize the likelihood then even if we maximize the first term i.e.&nbsp;<strong>ELBO</strong> that will work for us since second term will always be greater than 0</li>
<li>For example
<ul>
<li>Total Compensation = Base Salary + Bonus(<img src="https://latex.codecogs.com/png.latex?%5Cgeq%200">)</li>
<li>Total Compensation <img src="https://latex.codecogs.com/png.latex?%5Cgeq"> Base Salary</li>
</ul></li>
<li>Following the above analogy, we can also say that
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%7B%5Clog%7Dp_%7B%5Ctheta%7D(x)%20%5Cgeq%20%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)%7D%7Bq_%7B%5Cphi%7D(z%7Cx)%7D%5D"></li>
<li>So if we maximize the right side then left side will also be maximised</li>
</ul></li>
</ul>
</section>
<section id="rewriting-elbo" class="level3">
<h3 class="anchored" data-anchor-id="rewriting-elbo">Rewriting ELBO</h3>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)%7D%7Bq_%7B%5Cphi%7D(z%7Cx)%7D%5D%20=%20%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x%7Cz)p_%7B%5Ctheta%7D(z)%7D%7Bq_%7B%5Cphi%7D(z%7Cx)%7D%5D"> following chain rule of probability</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%5Clog%7Bp_%7B%5Ctheta%7D(x%20%7C%20z)%7D%5D%20+%20%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(z)%7D%7Bq_%7B%5Cphi%7D(z%7Cx)%7D%5D"> Split the expectation</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%5Clog%7Bp_%7B%5Ctheta%7D(x%20%7C%20z)%7D%5D%20-%20%20D_%7B%5Ctext%7BKL%7D%7D(q_%7B%5Cphi%7D(z%7Cx)%20%5C%7C%20p_%7B%5Ctheta%7D(z))"> Using KL Divergence</li>
<li>So to maximize the whole term we need to maximize the first one and minimize the second term</li>
<li>Profit = Revenue - Costs</li>
<li>To get maximum profit, we need to maximize revenue at the same time minimize the cost</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/variational-autoencoder/spaces.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
</section>
<section id="what-maximizing-elbo-means" class="level3">
<h3 class="anchored" data-anchor-id="what-maximizing-elbo-means">What Maximizing ELBO Means</h3>
<ul>
<li><p>Maximizing <strong>ELBO</strong> means:</p>
<ul>
<li><strong>Maximizing the first term</strong>: maximizing the reconstruction likelihood of the decoder</li>
<li><strong>Minimizing the second term</strong>: minimizing the distance between learned distribution and the prior belief we have over the latent variable</li>
</ul></li>
<li><p>When we want to maximize a function then we move in the direction of gradient</p></li>
<li><p>When we want to minimize a function then we move against the direction of gradient</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?L(%5Ctheta,%20%5Cphi,%20x)%20=%20%5Cmathbb%7BE%7D_%7Bz%20%5Csim%20q_%7B%5Cphi%7D(z%7Cx)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)%7D%7Bq_%7B%5Cphi%7D(z%7Cx)%7D%5D"> expectation over <img src="https://latex.codecogs.com/png.latex?%7Bq_%7B%5Cphi%7D(z%7Cx)%7D"></p></li>
</ul>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Note
</div>
</div>
<div class="callout-body-container callout-body">
<p>In theory we maximize ELBO. In code, we usually minimize the negative ELBO, which becomes reconstruction loss plus KL loss.</p>
</div>
</div>
<hr>
</section>
</section>
</section>
<section id="need-of-reparameterization" class="level1">
<h1>Need of Reparameterization</h1>
<section id="why-we-need-it" class="level2">
<h2 class="anchored" data-anchor-id="why-we-need-it">Why We Need It</h2>
<ul>
<li>In case of VAEs, Monte Carlo gradient estimator exhibits high variance thus giving random gradient directions.</li>
<li>The estimator is unbiased, meaning that even if at every step it may not be equal to the true expectation, on average it will converge to it, but as it is stochastic, it also has a variance and it happens to be high for practical use</li>
<li>And also a sampling process can’t be differentiated as in our case we are sampling from <img src="https://latex.codecogs.com/png.latex?z"> space to calculate loss</li>
</ul>
</section>
<section id="reparameterization-trick" class="level2">
<h2 class="anchored" data-anchor-id="reparameterization-trick">Reparameterization Trick</h2>
<ul>
<li>So we need a new estimator:- Let’s just move the source of randomness outside the model</li>
<li>Instead of directly sampling from <img src="https://latex.codecogs.com/png.latex?q_%7B%5Cphi%7D(z%7Cx)">, we rewrite sampling as
<ul>
<li>z = <img src="https://latex.codecogs.com/png.latex?%5Cmu_%7B%5Cphi%7D(x)%20+%20%5Csigma_%7B%5Cphi%7D(x)%5Cepsilon"> where <img src="https://latex.codecogs.com/png.latex?%5Cepsilon%20%5Csim%20%5Cmathcal%7BN%7D(0,%201)"></li>
</ul></li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/variational-autoencoder/reparam.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?L(%5Ctheta,%20%5Cphi,%20x)%20=%20%5Cmathbb%7BE%7D_%7Bp(%5Cepsilon)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)%7D%7Bq_%7B%5Cphi%7D(z%7Cx)%7D%5D"> expectation over <img src="https://latex.codecogs.com/png.latex?%7Bp(%5Cepsilon)%7D"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cepsilon%20%5Capprox%20p(%5Cepsilon)"></li>
<li><img src="https://latex.codecogs.com/png.latex?z%20=%20g(%5Cphi,%20x,%20%5Cepsilon)"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctilde%7BL%7D(%5Ctheta,%20%5Cphi,%20x)%20%5Coverset%7B%5Csim%7D%7B=%7D%20%5Cmathbb%7BE%7D_%7Bp(%5Cepsilon)%7D%5B%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)%7D%7Bq_%7B%5Cphi%7D(z%7Cx)%7D%5D"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctilde%7BL%7D(%5Ctheta,%20%5Cphi,%20x)%20=%20%7B%5Clog%7D%5Cfrac%7Bp_%7B%5Ctheta%7D(x,%20z)%7D%7Bq_%7B%5Cphi%7D(z%7Cx)%7D"></li>
</ul>
</section>
<section id="final-estimator" class="level2">
<h2 class="anchored" data-anchor-id="final-estimator">Final Estimator</h2>
<ul>
<li><p>Finally the resulting estimator for this model considering data point <img src="https://latex.codecogs.com/png.latex?x%5E%7B(i)%7D"> is:</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?%5Cmathcal%7BL%7D(%5Ctheta,%20%5Cphi;%20%5Cmathbf%7Bx%7D%5E%7B(i)%7D)%20%5Csimeq%20%5Cfrac%7B1%7D%7B2%7D%20%5Csum_%7Bj=1%7D%5E%7BJ%7D%20%5Cleft(1%20+%20%5Clog((%5Csigma_j%5E%7B(i)%7D)%5E2)%20-%20(%5Cmu_j%5E%7B(i)%7D)%5E2%20-%20(%5Csigma_j%5E%7B(i)%7D)%5E2%5Cright)%20+%20%5Cfrac%7B1%7D%7BL%7D%20%5Csum_%7Bl=1%7D%5E%7BL%7D%20%5Clog%20p_%7B%5Ctheta%7D(%5Cmathbf%7Bx%7D%5E%7B(i)%7D%20%7C%20%5Cmathbf%7Bz%7D%5E%7B(i,l)%7D)"></p></li>
<li><p>In above equation first term is KL-divergence and second term is Reconstruction loss(MSE)</p></li>
</ul>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Note
</div>
</div>
<div class="callout-body-container callout-body">
<p>MSE reconstruction loss comes from assuming a Gaussian decoder likelihood. If we assume a different decoder likelihood, the reconstruction loss can also change.</p>
</div>
</div>
</section>
</section>
<section id="code" class="level1">
<h1>Code</h1>
<ul>
<li>Below code is the simple implementation of how a VAE looks like in code</li>
<li>Notice in case of encoder, we predict log of variance because neural network might give negative numbers also.</li>
</ul>
<section id="vae-model" class="level2">
<h2 class="anchored" data-anchor-id="vae-model">VAE Model</h2>
<div id="d530b79d" class="cell" data-execution_count="1">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb1" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb1-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb1-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb1-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb1-4"></span>
<span id="cb1-5"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> VAE(nn.Module):</span>
<span id="cb1-6">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>):</span>
<span id="cb1-7">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb1-8">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.encoder <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Sequential(</span>
<span id="cb1-9">            nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">28</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">28</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">196</span>),</span>
<span id="cb1-10">            nn.Tanh(),</span>
<span id="cb1-11">            nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">196</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">48</span>),</span>
<span id="cb1-12">            nn.Tanh()</span>
<span id="cb1-13">        )</span>
<span id="cb1-14"></span>
<span id="cb1-15">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.mu_fc <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Sequential(</span>
<span id="cb1-16">            nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">48</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">16</span>),</span>
<span id="cb1-17">            nn.Tanh(),</span>
<span id="cb1-18">            nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">16</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>)</span>
<span id="cb1-19">        )</span>
<span id="cb1-20">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.logvar_fc <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Sequential(</span>
<span id="cb1-21">            nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">48</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">16</span>),</span>
<span id="cb1-22">            nn.Tanh(),</span>
<span id="cb1-23">            nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">16</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>)</span>
<span id="cb1-24">        )</span>
<span id="cb1-25">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.decoder <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Sequential(</span>
<span id="cb1-26">            nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">16</span>),</span>
<span id="cb1-27">            nn.Tanh(),</span>
<span id="cb1-28">            nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">16</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">48</span>),</span>
<span id="cb1-29">            nn.Tanh(),</span>
<span id="cb1-30">            nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">48</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">196</span>),</span>
<span id="cb1-31">            nn.Tanh(),</span>
<span id="cb1-32">            nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">196</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">28</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">28</span>),</span>
<span id="cb1-33">            nn.Tanh()</span>
<span id="cb1-34">        )</span>
<span id="cb1-35">    </span>
<span id="cb1-36">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> forward(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x):</span>
<span id="cb1-37">        <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##Encoding</span></span>
<span id="cb1-38">        mu, logvar <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.encode(x)</span>
<span id="cb1-39"></span>
<span id="cb1-40">        <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##Sampling</span></span>
<span id="cb1-41"></span>
<span id="cb1-42">        z <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.sample(mu, logvar)</span>
<span id="cb1-43"></span>
<span id="cb1-44">        <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">## Decoding</span></span>
<span id="cb1-45">        x <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.decode(z)</span>
<span id="cb1-46">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> mu, logvar, x</span>
<span id="cb1-47">    </span>
<span id="cb1-48">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> encode(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x):</span>
<span id="cb1-49">        x <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x.reshape(x.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>], <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">28</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">28</span>)</span>
<span id="cb1-50">        x <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.encoder(x)</span>
<span id="cb1-51">        mu, logvar <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.mu_fc(x), <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.logvar_fc(x)</span>
<span id="cb1-52">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> mu, logvar</span>
<span id="cb1-53">    </span>
<span id="cb1-54">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> decode(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x):</span>
<span id="cb1-55">        x <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.decoder(x)</span>
<span id="cb1-56">        x <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x.reshape(x.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>], <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">28</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">28</span>)</span>
<span id="cb1-57">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> x</span>
<span id="cb1-58">    </span>
<span id="cb1-59">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> sample(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, mu, log_var):</span>
<span id="cb1-60">        rand <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn_like(mu)</span>
<span id="cb1-61">        std <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.sqrt(torch.exp(log_var))</span>
<span id="cb1-62">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> rand <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> std <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> mu</span></code></pre></div></div>
</div>
</section>
<section id="losses" class="level2">
<h2 class="anchored" data-anchor-id="losses">Losses</h2>
<ul>
<li>Below is the code on how to get KL loss and reconstruction loss</li>
</ul>
<div id="b24b89ae" class="cell" data-execution_count="2">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb2" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb2-1"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> kl_loss(mu, log_var):</span>
<span id="cb2-2">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> torch.mean(<span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> torch.<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">sum</span>(torch.exp(log_var) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> mu<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> log_var, dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>))</span>
<span id="cb2-3"></span>
<span id="cb2-4"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> recon_loss(pred, target):</span>
<span id="cb2-5">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> F.mse_loss(pred, target)</span></code></pre></div></div>
</div>
</section>
</section>
<section id="why-vaes-produce-blurry-samples" class="level1">
<h1>Why VAEs Produce Blurry Samples</h1>
<ul>
<li>Multiple possible images can correspond to similar latent representations. When many plausible images map to nearby latent regions, the decoder tends to generate an averaged reconstruction.</li>
<li>This overlap occurs partly because of KL regularization, where the encoder is forced to keep latent representations close to a simple prior distribution (usually a Gaussian). As a result, different images may occupy overlapping regions in latent space.</li>
<li>Additionally, VAEs typically assume the decoder output follows a Gaussian distribution:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?p(x%7Cz)%20=%20%5Cmathcal%7BN%7D(%5Cmu_%7B%5Ctheta%7D(z),%20%5Csigma%5E2%5Cmathbf%7BI%7D)"></li>
</ul></li>
<li>Due to this assumption, maximizing likelihood becomes equivalent to minimizing Mean Squared Error (MSE) between the real and predicted image.</li>
<li>Now suppose two possible pixel values for a region are 0 and 1 for similar latent vectors. Under MSE, the optimal prediction becomes their average:
<ul>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7B0+1%7D%7B2%7D%20=%200.5"></li>
</ul></li>
<li>Therefore, instead of producing one sharp possibility, the decoder learns to predict averaged pixel values across multiple plausible outputs, leading to blurry images.</li>
</ul>
<hr>
</section>
<section id="summary" class="level1">
<h1>Summary</h1>
<ul>
<li>Encoder learns <img src="https://latex.codecogs.com/png.latex?q_%7B%5Cphi%7D(z%7Cx)"></li>
<li>Decoder learns <img src="https://latex.codecogs.com/png.latex?p_%7B%5Ctheta%7D(x%7Cz)"></li>
<li>KL-divergence keeps latent distribution close to prior distribution</li>
<li>Reconstruction loss helps preserve input information</li>
<li>Reparameterization helps backpropagate through sampling</li>
</ul>


</section>

 ]]></description>
  <category>Generative AI</category>
  <guid>https://riteshrm.github.io/posts/variational-autoencoder/</guid>
  <pubDate>Wed, 06 May 2026 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/variational-autoencoder/vae_thumbnail_resized.png" medium="image" type="image/png" height="82" width="144"/>
</item>
<item>
  <title>Rotary Position Embedding</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/rotary-position-embedding/</link>
  <description><![CDATA[ 





<ul>
<li>In this post we will try to understand RoPE.</li>
<li>This is mostly based on <a href="https://www.youtube.com/watch?v=qKUobBR5R1A">Why Rotating Vectors Solves Positional Encoding in Transformers</a></li>
</ul>
<section id="why-relative-position-embedding" class="level2">
<h2 class="anchored" data-anchor-id="why-relative-position-embedding">Why Relative Position Embedding?</h2>
<ul>
<li><p>It captures how two tokens are positioned with respect to each other</p></li>
<li><p>For Example:-</p>
<ul>
<li><pre class="text"><code>  my daughter called her brother last night  [Sentence:-1]
  0     1 (n)  2 (m)  3    4      5     6</code></pre></li>
<li>Absolute Position Embedding of token daughter depends on position of token i.e.&nbsp;1 (n)</li>
<li>Relative Position Embedding of token ‘daughter’ with respect to token ‘called’ -1 (n-m)
<ul>
<li>Where -1 or in general it will tell whether token ‘daughter’ is before or after ‘called’ and at what distance.</li>
</ul></li>
</ul></li>
<li><p>Query at position m attends Key at position n and to calculate attention score, it depends more on relative position than absolute position.</p></li>
<li><pre class="text"><code>  last night my daughter called her brother  [Sentence:-2]
  0      1    2    3        4    5     6</code></pre></li>
<li><p>In above sentence even though the APE is different compared to previous sentence their RPE is still the same</p></li>
<li><p>In case of APE, there is linear relationship between tokens at pos and pos + k, and we expect our model to learn this relationship</p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?PE_%7Bpos%20+%20k%7D"> = <img src="https://latex.codecogs.com/png.latex?T%5Ek"> * <img src="https://latex.codecogs.com/png.latex?PE_%7Bpos%7D"></li>
</ul></li>
<li><p>In case of RPE, we are explicitly telling our model that these two tokens are at k tokens apart</p></li>
<li><p>Below table defines a summary of APE vs RPE</p></li>
</ul>
<table class="caption-top table">
<colgroup>
<col style="width: 9%">
<col style="width: 31%">
<col style="width: 59%">
</colgroup>
<thead>
<tr class="header">
<th style="text-align: center;">Sentence</th>
<th style="text-align: center;">APE</th>
<th style="text-align: center;">RPE</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td style="text-align: center;">1</td>
<td style="text-align: center;">tokens are at 1st and 2nd Position</td>
<td style="text-align: center;">tokens are at (-1) tokens apart, where daughter comes before called</td>
</tr>
<tr class="even">
<td style="text-align: center;">2</td>
<td style="text-align: center;">tokens are at 1st and 2nd Position</td>
<td style="text-align: center;">tokens are at (-1) tokens apart, where daughter comes before called</td>
</tr>
</tbody>
</table>
<ul>
<li>As we can generalise from above table that the two tokens which generally comes together or at k tokens apart, RPE will be same in such cases whereas in case of APE, it will differ for each sentence which model have to learn to generalise better</li>
<li>So instead of saying i am at this position or that position, it would be better to explicitly mention that we are at k tokens apart</li>
</ul>
</section>
<section id="rope" class="level1">
<h1>RoPE</h1>
<ul>
<li><p>Let’s say we have a 2D vector and we want to rotate it by angle <img src="https://latex.codecogs.com/png.latex?%5Ctheta">, where it was earlier at <img src="https://latex.codecogs.com/png.latex?%5Calpha"> with magnitude r</p></li>
<li><p>We can write initial <img src="https://latex.codecogs.com/png.latex?x"> and <img src="https://latex.codecogs.com/png.latex?y"> as:</p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x"> = <img src="https://latex.codecogs.com/png.latex?r*%5Ccos(%5Ctheta)"></li>
<li><img src="https://latex.codecogs.com/png.latex?y"> = <img src="https://latex.codecogs.com/png.latex?r*%5Csin(%5Ctheta)"></li>
</ul></li>
<li><p>If we rotate it by <img src="https://latex.codecogs.com/png.latex?%5Calpha">, then:</p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?x'"> = <img src="https://latex.codecogs.com/png.latex?r*%5Ccos(%5Ctheta%20+%20%5Calpha)"> = <img src="https://latex.codecogs.com/png.latex?r(%5Ccos(%5Ctheta)%5Ccos(%5Calpha)%20-%20%5Csin(%5Ctheta)%5Csin(%5Calpha))"></li>
<li><img src="https://latex.codecogs.com/png.latex?y'"> = <img src="https://latex.codecogs.com/png.latex?r*%5Csin(%5Ctheta%20+%20%5Calpha)"> = <img src="https://latex.codecogs.com/png.latex?r(%5Csin(%5Ctheta)%5Ccos(%5Calpha)%20+%20%5Ccos(%5Ctheta)%5Csin(%5Calpha))"></li>
</ul></li>
<li><p>If we represent: <img src="https://latex.codecogs.com/png.latex?%0AR(%5Ctheta)%20=%20%5Cbegin%7Bbmatrix%7D%0A%5Ccos(%5Ctheta)%20&amp;%20-%5Csin(%5Ctheta)%20%5C%5C%0A%5Csin(%5Ctheta)%20&amp;%20%5Ccos(%5Ctheta)%20%5C%5C%0A%5Cend%7Bbmatrix%7D%0A"></p>
<p><img src="https://latex.codecogs.com/png.latex?%0Az'%20=%20%5Cbegin%7Bbmatrix%7D%0Ax'%20%5C%5C%0Ay'%20%5C%5C%0A%5Cend%7Bbmatrix%7D%0A"></p>
<p><img src="https://latex.codecogs.com/png.latex?%0Az%20=%20%5Cbegin%7Bbmatrix%7D%0Ax%20%5C%5C%0Ay%20%5C%5C%0A%5Cend%7Bbmatrix%7D%0A"></p></li>
<li><p>Then we can write <img src="https://latex.codecogs.com/png.latex?z'%20=%20R(%5Ctheta)z"></p></li>
<li><p>Below two properties which will be used later:</p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?R(-%5Ctheta)"> = <img src="https://latex.codecogs.com/png.latex?R(%5Ctheta)%5ET"> which gives</li>
<li><img src="https://latex.codecogs.com/png.latex?R(%5Ctheta)%5ET"> <img src="https://latex.codecogs.com/png.latex?R(%5Ctheta)"> = I [Identity Matrix]</li>
<li><img src="https://latex.codecogs.com/png.latex?R(%5Ctheta_%7B1%7D)"> <img src="https://latex.codecogs.com/png.latex?R(%5Ctheta_%7B2%7D)"> = <img src="https://latex.codecogs.com/png.latex?R(%5Ctheta_%7B1%7D%20+%20%5Ctheta_%7B2%7D)"></li>
</ul></li>
<li><p>RoPE rotates the embeddings</p></li>
<li><p>Let’s say q(query) at m and k(key) at n</p></li>
<li><p>Then dot product between q and k would be</p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?(R(m%5Ctheta)q_%7Bm%7D)%5ETR(n%5Ctheta)k_%7Bn%7D"></li>
<li>= <img src="https://latex.codecogs.com/png.latex?q_%7Bm%7D%5ETR(m%5Ctheta)R(n%5Ctheta)k_%7Bn%7D"></li>
<li>Since <img src="https://latex.codecogs.com/png.latex?R(-%5Ctheta)"> = <img src="https://latex.codecogs.com/png.latex?R(%5Ctheta)%5ET">, so <img src="https://latex.codecogs.com/png.latex?R(-m%5Ctheta)"> = <img src="https://latex.codecogs.com/png.latex?R(m%5Ctheta)%5ET"></li>
<li>this gives <img src="https://latex.codecogs.com/png.latex?q_%7Bm%7D%5ETR(-m%5Ctheta)R(n%5Ctheta)k_%7Bn%7D"></li>
<li>now since <img src="https://latex.codecogs.com/png.latex?R(%5Ctheta_%7B1%7D)"> <img src="https://latex.codecogs.com/png.latex?R(%5Ctheta_%7B2%7D)"> = <img src="https://latex.codecogs.com/png.latex?R(%5Ctheta_%7B1%7D%20+%20%5Ctheta_%7B2%7D)"></li>
<li>this gives <img src="https://latex.codecogs.com/png.latex?q_%7Bm%7D%5ETR((n-m)%5Ctheta)k_%7Bn%7D"></li>
<li>In above eqn attention score now explicitly depends on relative distance between q and k</li>
<li>So if relative distance changes then only this factor will change</li>
</ul></li>
</ul>
<section id="implementation" class="level3">
<h3 class="anchored" data-anchor-id="implementation">Implementation</h3>
<ul>
<li>Treat a pair as single 2D vector space and rotate it independently</li>
<li>For example lets say we have d_model of 256 then we will have 128 2D vectors and we can rotate those pairs independently as shown in below table</li>
</ul>
<table class="caption-top table">
<colgroup>
<col style="width: 23%">
<col style="width: 76%">
</colgroup>
<thead>
<tr class="header">
<th style="text-align: center;">Pairs</th>
<th style="text-align: center;">Rotation Matrix</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td style="text-align: center;"><img src="https://latex.codecogs.com/png.latex?(e_%7B1%7D,%20e_%7B2%7D)"></td>
<td style="text-align: center;"><img src="https://latex.codecogs.com/png.latex?R(m%5Ctheta_%7B1%7D)"></td>
</tr>
<tr class="even">
<td style="text-align: center;"><img src="https://latex.codecogs.com/png.latex?(e_%7B3%7D,%20e_%7B4%7D)"></td>
<td style="text-align: center;"><img src="https://latex.codecogs.com/png.latex?R(m%5Ctheta_%7B2%7D)"></td>
</tr>
<tr class="odd">
<td style="text-align: center;">……………..</td>
<td style="text-align: center;">…………</td>
</tr>
<tr class="even">
<td style="text-align: center;">……………..</td>
<td style="text-align: center;">…………</td>
</tr>
<tr class="odd">
<td style="text-align: center;"><img src="https://latex.codecogs.com/png.latex?(e_%7Bd_%7Bmodel%7D/2-1%7D,%20e_%7Bd_%7Bmodel%7D/2%7D)"></td>
<td style="text-align: center;"><img src="https://latex.codecogs.com/png.latex?R(m%5Ctheta_%7Bd_%7Bmodel%7D/2%7D)"></td>
</tr>
</tbody>
</table>
<ul>
<li>where
<ul>
<li><img src="https://latex.codecogs.com/png.latex?e_%7Bk%7D"> is embedding value at index k</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctheta_%7Bi%7D"> is rotation angle given as <img src="https://latex.codecogs.com/png.latex?%5Ctheta_%7Bi%7D"> = <img src="https://latex.codecogs.com/png.latex?10000%5E%7B-2(i-1)/d_%7Bmodel%7D%7D">, where i runs from 1 to <img src="https://latex.codecogs.com/png.latex?d_%7Bmodel%7D/2"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctheta_%7Bi%7D"> decreases as i increases, so initial embedding values are rotated by large angles as compared to later embedding values</li>
</ul></li>
<li>Below is the code to get <img src="https://latex.codecogs.com/png.latex?(R(%5Ctheta)"> and also validate if <img src="https://latex.codecogs.com/png.latex?R(%5Ctheta)%5ET"> <img src="https://latex.codecogs.com/png.latex?R(%5Ctheta)"> = I [Identity Matrix]</li>
<li>For simplicity, i have just printed a single matrix</li>
</ul>
<div id="0b5b0c4c" class="cell" data-execution_count="1">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb3" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb3-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb3-2"></span>
<span id="cb3-3"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_RoPE(pos, d_model):</span>
<span id="cb3-4">    theta <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor([<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">10000</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span>(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>(i<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>d_model) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, d_model<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)])</span>
<span id="cb3-5">    bsz, seq_len<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> pos.shape</span>
<span id="cb3-6">    cos <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.cos(pos[:, :, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>]<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> theta[<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>, :]).view(bsz, seq_len, d_model<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>)</span>
<span id="cb3-7">    sin <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.sin(pos[:, :, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>]<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> theta[<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>, :]).view(bsz, seq_len, d_model<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>)</span>
<span id="cb3-8">    row1 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.stack([cos, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>sin], dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb3-9">    row2 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.stack([sin, cos], dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb3-10"></span>
<span id="cb3-11">    RTheta <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.stack([row1, row2], dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>)</span>
<span id="cb3-12">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> RTheta</span>
<span id="cb3-13"></span>
<span id="cb3-14">bsz <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span></span>
<span id="cb3-15">tokens <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor([[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>] <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> _ <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(bsz)])</span>
<span id="cb3-16">d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">256</span></span>
<span id="cb3-17"></span>
<span id="cb3-18">RTheta <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> get_RoPE(tokens, d_model)</span>
<span id="cb3-19"></span>
<span id="cb3-20">matrix <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.matmul(RTheta, RTheta.transpose(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>))</span>
<span id="cb3-21"></span>
<span id="cb3-22">matrix[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>][<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>][<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>]</span></code></pre></div></div>
<div class="cell-output cell-output-display" data-execution_count="1">
<pre><code>tensor([[1.0000, 0.0000],
        [0.0000, 1.0000]])</code></pre>
</div>
</div>
<ul>
<li>Below Code shows how to integrate RoPE while calculating attention</li>
</ul>
<div id="daa758ad" class="cell" data-execution_count="2">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb5" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb5-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb5-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb5-3"></span>
<span id="cb5-4"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> SimpleAttention(nn.Module):</span>
<span id="cb5-5">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, d_model, hidden_dim):</span>
<span id="cb5-6">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb5-7">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.hidden_dim <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> hidden_dim</span>
<span id="cb5-8">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.q <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> hidden_dim)</span>
<span id="cb5-9">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> hidden_dim)</span>
<span id="cb5-10">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.v <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> hidden_dim)</span>
<span id="cb5-11">    </span>
<span id="cb5-12">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> forward(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x, rotary_emb):</span>
<span id="cb5-13">        bsz, seq_len, d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x.shape</span>
<span id="cb5-14">        query <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.q(x)</span>
<span id="cb5-15">        key <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.k(x)</span>
<span id="cb5-16">        value <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.v(x)</span>
<span id="cb5-17"></span>
<span id="cb5-18">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> rotary_emb <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">not</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>:</span>
<span id="cb5-19">            bsz, seq_len, d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x.shape</span>
<span id="cb5-20">            query <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> query.view(bsz, seq_len, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.hidden_dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb5-21">            key <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> key.view(bsz, seq_len, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.hidden_dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb5-22">            query <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>  torch.matmul(rotary_emb, query).view(bsz, seq_len, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.hidden_dim)</span>
<span id="cb5-23">            key <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>  torch.matmul(rotary_emb, key).view(bsz, seq_len, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.hidden_dim)</span>
<span id="cb5-24">        </span>
<span id="cb5-25">        scores <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.softmax(torch.matmul(query, key.transpose(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.hidden_dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>), dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb5-26">        final <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.matmul(scores, value)</span>
<span id="cb5-27">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> final</span>
<span id="cb5-28"></span>
<span id="cb5-29">bsz <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span></span>
<span id="cb5-30">tokens <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor([[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>] <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> _ <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(bsz)])</span>
<span id="cb5-31">d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">256</span></span>
<span id="cb5-32">embedding <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>tokens.shape, d_model)</span>
<span id="cb5-33"></span>
<span id="cb5-34">RTheta <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> get_RoPE(tokens, d_model)</span>
<span id="cb5-35"></span>
<span id="cb5-36">model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> SimpleAttention(d_model, d_model)</span>
<span id="cb5-37"></span>
<span id="cb5-38">out <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> model(embedding, RTheta)</span>
<span id="cb5-39"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(out.shape)</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<pre><code>torch.Size([2, 2, 256])</code></pre>
</div>
</div>
</section>
<section id="the-10000" class="level3">
<h3 class="anchored" data-anchor-id="the-10000">The 10000</h3>
<ul>
<li><p>As relative distance increases, the contribution of later dimension of embedding also increases in attention calculation.</p>
<ul>
<li>For example, for smaller relative distance, the earlier dimensions only change but not the later ones as we can see in below figure, thus only earlier dimensions contribute to attention
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/rotary-position-embedding/smaller_rd.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure></li>
<li>for larger relative distance, later dimensions also get under significant modification as we can see in below figure, thus earlier as well as later dimensions contribute to attention
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/rotary-position-embedding/larger_rd.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure></li>
</ul></li>
<li><p>Why 10000?</p>
<ul>
<li>If we chose some smaller value, then even later dimensions gets modified aggressively for smaller relative distances and thus changing the attention score aggressively</li>
<li>If we chose some larger value then even earlier dimensions didn’t get modified for larger relative distances and thus attention does not change much at all, the relative distance must need to be much larger for significant contribution to attention.</li>
<li>Basically this calculates how quickly attention gets sensitive to relative positional difference</li>
<li>As relative distance increases, the cosine similarity decreases [Attention Decay], and this is what we want, closer tokens attend to each other more than tokens far apart from each other as we can see from below figure.
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/rotary-position-embedding/attention_decay.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure></li>
</ul></li>
<li><p>Llama 3 used 500,000 as base frequency stating that it will lower the attention decay and thus model will be able to attend far apart tokens more meaningfully</p></li>
<li><p>As we can see in below figure, cosine similarity decreases very smoothly, thus will help in case of longer contexts</p>
<figure style="text-align: center;" class="figure">
<p><img src="https://riteshrm.github.io/posts/rotary-position-embedding/attention_decay500k.png" style="width:80%" class="figure-img"></p>
<figcaption>
</figcaption>
</figure></li>
<li><p>It was believed that due to this attention decay, RoPE works very well</p></li>
<li><p>But <a href="https://arxiv.org/abs/2410.06205">Round and Round We Go! What makes Rotary Positional Encodings useful?</a> finds out something else is working under the hood which makes rope good at positional encoding.</p>
<ul>
<li>They found out that this decay happens only in specific scenarios</li>
<li>If two embeddings had negative cosine similarity then instead of decreasing they might increase.</li>
<li>So what makes rope good
<ul>
<li>Lower Dimension Embeddings : High Frequency</li>
<li>Later Dimension Embeddings : Low Frequency</li>
<li>Low frequency dimensions dominate the attention dot product, whereas high frequency dimensions rotates heavily thus heavily dominated by positional information.</li>
<li>Semantic heads rely heavily on low frequency dimensions as a result even if distance increases, it has minimal impact on semantic dot product in case of long context if we chose 500k</li>
<li>If we have long context and base frequency is 10k then it is possible that for large position difference even the low frequency dimensions might have gone under aggressive transformation, thus heavily impacting the semantic attention</li>
<li>And if we chose 500k then the low frequency dimensions will not go under heavy rotation thus preserving the semantic meaning and helping to cover long range context</li>
</ul></li>
<li>So we can say that:
<ul>
<li>High Frequency means positional information encoding.</li>
<li>Low Frequency means semantic information encoding.</li>
</ul></li>
</ul></li>
</ul>


</section>
</section>

 ]]></description>
  <category>Deep Learning</category>
  <guid>https://riteshrm.github.io/posts/rotary-position-embedding/</guid>
  <pubDate>Tue, 07 Apr 2026 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/rotary-position-embedding/rotary_thumbnail_resized.png" medium="image" type="image/png" height="82" width="144"/>
</item>
<item>
  <title>Position Encoding</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/position-encoding/</link>
  <description><![CDATA[ 





<ul>
<li>This is mostly based on <a href="https://www.youtube.com/watch?v=dWkm4nFikgM">Positional Encoding in Transformer</a></li>
</ul>
<section id="positional-encoding-pe" class="level1">
<h1>Positional Encoding (PE)</h1>
<ul>
<li>RNNs process tokens sequentially so they have information about the position of tokens of a given sequence.</li>
<li>Transformers process all the tokens simultaneously where each token attends to every other token.</li>
<li><em>For Example:</em>:-
<ul>
<li>my daughter called her brother [where each word is a token]</li>
<li>in above sentence <strong>my</strong> will attend to all other tokens and similarly others will also attend other tokens.</li>
<li>now consider other permutation of above sequence her daughter called my brother</li>
<li>even in above example, permutation is different but transformers will find out the same context for each word as above one</li>
<li>a simple explanation would be consider <strong>my</strong> and <strong>her</strong>
<ul>
<li>the attention between these will be same for both of the sequences, but both of them corresponds to different meaning.</li>
<li>so to have different attentions for different sequences we need to inject some information about the positions of words also.</li>
</ul></li>
</ul></li>
</ul>
<hr>
</section>
<section id="attempted-solution" class="level1">
<h1>Attempted Solution</h1>
<ul>
<li><p>Use the index of tokens directly as position information for a given sequence. However, when we add token embedding with this position indices, positional information will overpower the content signal and also, the rightmost tokens will dominate.</p></li>
<li><p>Now, to solve this, we can normalize the positional information i.e.&nbsp;normalize with the length of sequence. But now we have another problem, all of the sequences will never be of same length, so each position information will keep varying. For example lets consider two sequences</p>
<ol type="1">
<li>I am going PE:=[0/3 1/3 2/3]</li>
<li>All of us are going PE:=[0/5 1/5 2/5]</li>
</ol></li>
<li><p>As we can see in above example, in sequence we are normalizing by 3 and in 2nd one by 5, which is not good for a model to learn like one time we are saying that 2nd positions value is 0.33 and in the next sequence we are saying no no, its 0.2</p></li>
</ul>
<hr>
</section>
<section id="sinusoidal-positional-encoding" class="level1">
<h1>Sinusoidal Positional Encoding</h1>
<ul>
<li><p>The authors of the Transformer paper introduced sinusoidal functions to address this issue.</p></li>
<li><p>The positional encoding is defined as:</p>
<ul>
<li>For even indices:</li>
</ul>
<p><img src="https://latex.codecogs.com/png.latex?%0APE(pos,%202i)%20=%20%5Csin%5Cleft(%5Cfrac%7Bpos%7D%7B10000%5E%7B%5Cfrac%7B2i%7D%7Bd_%7Bmodel%7D%7D%7D%7D%5Cright)%0A"></p>
<ul>
<li>For odd indices:</li>
</ul></li>
</ul>
<p><img src="https://latex.codecogs.com/png.latex?%0APE(pos,%202i%20+%201)%20=%20%5Ccos%5Cleft(%5Cfrac%7Bpos%7D%7B10000%5E%7B%5Cfrac%7B2i%7D%7Bd_%7Bmodel%7D%7D%7D%7D%5Cright)%0A"></p>
<ul>
<li><em>where</em>
<ul>
<li>pos is the position of token</li>
<li><img src="https://latex.codecogs.com/png.latex?d_%7Bmodel%7D"> is dimensionality of position embedding</li>
<li>i is index of embedding dimension where i runs from 0 to <img src="https://latex.codecogs.com/png.latex?d_%7Bmodel%7D">/2 -1 [each value of i corresponds to one frequency of sinusoid]</li>
</ul></li>
</ul>
<section id="below-is-python-code-for-getting-1d-sinusoidal-position-embedding" class="level2">
<h2 class="anchored" data-anchor-id="below-is-python-code-for-getting-1d-sinusoidal-position-embedding">Below is python code for getting 1D Sinusoidal Position Embedding</h2>
<div id="98558041" class="cell" data-execution_count="1">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb1" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb1-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb1-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">from</span> typing <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> Union</span>
<span id="cb1-3"></span>
<span id="cb1-4"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_1d_sin_cos_pe(d_model:<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">int</span>, pos:Union[<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">int</span>, <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">list</span>]):</span>
<span id="cb1-5">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">type</span>(pos)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">==</span><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">int</span>:</span>
<span id="cb1-6">        pos <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [pos]</span>
<span id="cb1-7">    n_tokens <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">len</span>(pos)</span>
<span id="cb1-8">    pos <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor(pos).reshape(n_tokens, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb1-9">    div_term <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor([<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">10000</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span>(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span>i<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>d_model) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(d_model<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>)])</span>
<span id="cb1-10">    sinPE <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.sin(pos<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>div_term)</span>
<span id="cb1-11">    cosPE <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.cos(pos<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>div_term)</span>
<span id="cb1-12">    combinedPE <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.zeros(n_tokens, d_model)</span>
<span id="cb1-13">    combinedPE[:, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>::<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> sinPE</span>
<span id="cb1-14">    combinedPE[:, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>::<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> cosPE</span>
<span id="cb1-15"></span>
<span id="cb1-16">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> combinedPE</span>
<span id="cb1-17"></span>
<span id="cb1-18"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># For single position</span></span>
<span id="cb1-19">d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb1-20">pos <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span></span>
<span id="cb1-21">pe2 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> get_1d_sin_cos_pe(d_model, pos)</span>
<span id="cb1-22"></span>
<span id="cb1-23">d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb1-24">pos <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span></span>
<span id="cb1-25">pe3 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> get_1d_sin_cos_pe(d_model, pos)</span>
<span id="cb1-26"></span>
<span id="cb1-27">combinedPE <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.cat([pe2, pe3], dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>)</span>
<span id="cb1-28"></span>
<span id="cb1-29"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># For multiple positions </span></span>
<span id="cb1-30">d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb1-31">pos <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>]</span>
<span id="cb1-32">pe <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> get_1d_sin_cos_pe(d_model, pos)</span>
<span id="cb1-33"></span>
<span id="cb1-34"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(torch.equal(combinedPE, pe))</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<pre><code>True</code></pre>
</div>
</div>
</section>
<section id="lets-see-only-sine-for-intuition" class="level2">
<h2 class="anchored" data-anchor-id="lets-see-only-sine-for-intuition">Lets see only sine for intuition</h2>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/scale_factor.png" style="width:80%" class="figure-img">
<figcaption>
As dimension index increases, scaling factor also increases
</figcaption>
</figure>
<ul>
<li><p>As the scaling factor increases, the period of sin wave increases frequency decreases i.e.&nbsp;the repetition of values decreases.</p></li>
<li><p>We can also say that as scale factor increases, the oscillation becomes slower.</p></li>
<li><p>Dimension 0 i.e.&nbsp;lower dimension can incorporate fine grained local positional information.</p></li>
<li><p>Value at k is far different than value at k + 5 as we can see from below figure.</p></li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/dim_0_sin.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<hr>
<ul>
<li>Dimension 255 i.e.&nbsp;higher dimensions incorporates global positional information</li>
<li>Value at k and k+5 is nearly similar but at k and k+200 is quite different as we can see from the below figure.</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/dim_255_sin.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<hr>
<ul>
<li>Basically given a particular position pos, it gets mapped to various sine waves which incorporates local as well as global information as we can see from below figure.</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/sine_wave.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
</section>
<section id="key-observations" class="level2">
<h2 class="anchored" data-anchor-id="key-observations">Key Observations</h2>
<ul>
<li>Earlier indices (smaller ( i )):
<ul>
<li>Capture <strong>short-range information</strong></li>
<li>High-frequency variations</li>
</ul></li>
<li>Later indices (larger ( i )):
<ul>
<li>Capture <strong>long-range information</strong></li>
<li>Low-frequency variations</li>
</ul></li>
<li>This creates a mix of:
<ul>
<li>Short-range patterns (rapid oscillations)</li>
<li>Long-range patterns (slow oscillations)</li>
</ul></li>
</ul>
</section>
<section id="connection-to-binary-encoding" class="level2">
<h2 class="anchored" data-anchor-id="connection-to-binary-encoding">Connection to Binary Encoding</h2>
<ul>
<li>As frequency decreases, <strong>bit significance increases</strong></li>
<li>Similar to binary representation:
<ul>
<li>Rightmost bits → change frequently (low significance)</li>
<li>Leftmost bits → change slowly (high significance)</li>
</ul></li>
<li>Moving from right → left:
<ul>
<li>Repetition decreases</li>
<li>Importance increases</li>
</ul></li>
<li>And this is what we want from a positional encoding, where it can help in differentiate local as well as global tokens.</li>
<li>But since Binary Encodings are discrete and does not change smoothly for example BE of 3 is 11 and BE of 4 is 100, which is not continuous whereas sinusoidal waves are continuous and change smoothly from pos to pos + 1.</li>
</ul>
<hr>
<section id="locality-insight" class="level3">
<h3 class="anchored" data-anchor-id="locality-insight">Locality Insight</h3>
<p>For small values of i:</p>
<ul>
<li>PE(pos) and PE(pos + 1) are <strong>very different</strong></li>
<li>PE(pos) and PE(pos + k) are <strong>more similar for larger k</strong></li>
</ul>
<p>Implication:</p>
<ul>
<li>Helps distinguish <strong>nearby tokens</strong></li>
</ul>
<hr>
</section>
<section id="global-insight" class="level3">
<h3 class="anchored" data-anchor-id="global-insight">Global Insight</h3>
<p>For large values of i:</p>
<ul>
<li>PE(pos) and PE(pos + 1) are <strong>more similar</strong></li>
<li>PE(pos) and PE(pos + k) are <strong>very different for larger k</strong></li>
</ul>
<p>Implication:</p>
<ul>
<li>Helps distinguish <strong>Far-apart tokens</strong></li>
</ul>
<hr>
</section>
</section>
</section>
<section id="why-10000" class="level1">
<h1>Why 10000?</h1>
<section id="what-happens-if-we-chose-100" class="level2">
<h2 class="anchored" data-anchor-id="what-happens-if-we-chose-100">What happens if we chose 100</h2>
<ul>
<li>From below graph we can see that even higher dimension starts repeating themselves i.e.&nbsp;their frequency increases and thus we cant distinguish between far-apart tokens</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/100_SF.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<ul>
<li>For example lets calculate cosine similarity between PE[128:256] of 500th position to everyone other position.</li>
<li>The cosine similarity will change drastically as we can see in the below figure, whereas we want higher dimensions to change smoothly.</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/cs2_100.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<ul>
<li>The cosine similarity between PE[0:128] of 500th position to everyone other position.</li>
<li>The cosine similarity decreases drastically to zero even with position difference of 10 only, whereas we want it to decrease smoothly but not in an aggressive way.</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/cs1_100.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
</section>
<section id="what-happens-if-we-chose-100000" class="level2">
<h2 class="anchored" data-anchor-id="what-happens-if-we-chose-100000">What happens if we chose 100000</h2>
<ul>
<li>And if we chose 100K as scaling factor then from below figure we can see that even the earlier dimensions have reduced frequency and thus we can’t differentiate between two local positions</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/100k_SF.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<ul>
<li>For example lets calculate cosine similarity between PE[128:256] of 500th position to everyone other position, in this case similarity barely changes as we can see from below figure.</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/cs2_100k.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<ul>
<li>The cosine similarity between PE[0:128] of 500th position to everyone other position.</li>
<li>The cosine similarity remains mostly same even with position difference of 50, whereas we want it to decrease smoothly.</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/cs1_100k.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
</section>
<section id="how-does-10k-solves-above-problems" class="level2">
<h2 class="anchored" data-anchor-id="how-does-10k-solves-above-problems">How does 10k solves above problems</h2>
<ul>
<li>And as suggested in paper, if we chose 10k. It is something like sweet spot where earlier dimensions have higher frequency thus helping in distinguishing between local positions and later dimensions have lower frequency thus helping in capturing long range positional differences.</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/10k_SF.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<ul>
<li>As we can see from below graphs it solves the problem of cosine similarity between PE of 500th position and every other position</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/cs2_10k.png" style="width:80%" class="figure-img">
<figcaption>
Higher dimension similarity changes smoothly to capture global information
</figcaption>
</figure>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/cs1_10k.png" style="width:80%" class="figure-img">
<figcaption>
Lower dimension similarity changes somewhat aggressively to capture local information
</figcaption>
</figure>
</section>
</section>
<section id="why-include-cosine-also" class="level1">
<h1>Why include cosine also</h1>
<ul>
<li>It allows, the PE across all positions to have simple linear relationship.</li>
<li>Generally:
<ul>
<li>x = <img src="https://latex.codecogs.com/png.latex?%5Ccos(%5Ctheta)"></li>
<li>y = <img src="https://latex.codecogs.com/png.latex?%5Csin(%5Ctheta)"></li>
</ul></li>
<li>But in paper:
<ul>
<li>x = <img src="https://latex.codecogs.com/png.latex?%5Csin(%5Ctheta)"></li>
<li>y = <img src="https://latex.codecogs.com/png.latex?%5Ccos(%5Ctheta)"></li>
</ul></li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/first_cos.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/first_cos2.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/position-encoding/first_cos3.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<ul>
<li>As we can see from above equations, PE[pos+k] = <img src="https://latex.codecogs.com/png.latex?T_%7Bk%7D"> PE[pos]</li>
</ul>


</section>

 ]]></description>
  <category>Deep Learning</category>
  <guid>https://riteshrm.github.io/posts/position-encoding/</guid>
  <pubDate>Mon, 06 Apr 2026 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/position-encoding/thumbnail.png" medium="image" type="image/png" height="96" width="144"/>
</item>
<item>
  <title>AI Engineering: Chapter-Wise Summary</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/ai-engineering/</link>
  <description><![CDATA[ 





<ul>
<li>This is completely based on <a href="https://www.oreilly.com/library/view/ai-engineering/9781098166298/">AI Engineering By Chip Huyen</a></li>
</ul>
<section id="chapter-1-introduction-to-building-ai-applications-with-foundation-models" class="level1">
<h1>Chapter 1 Introduction to Building AI Applications with Foundation Models</h1>
<section id="language-models-lms" class="level2">
<h2 class="anchored" data-anchor-id="language-models-lms">Language Models (LMs)</h2>
<section id="masked-language-models-mlm" class="level3">
<h3 class="anchored" data-anchor-id="masked-language-models-mlm">Masked Language Models (MLM)</h3>
<ul>
<li>Predict missing tokens in a sentence<br>
<em>Example:</em> <code>My favorite __ is blue</code></li>
<li>Use <strong>bidirectional context</strong> (both previous and next tokens)</li>
<li>Common use cases:
<ul>
<li>Sentiment analysis</li>
<li>Text classification</li>
<li>Code debugging (requires full contextual understanding)</li>
</ul></li>
<li><strong>Example:</strong> BERT (Bidirectional Encoder Representations from Transformers)</li>
</ul>
</section>
<section id="generative-language-models" class="level3">
<h3 class="anchored" data-anchor-id="generative-language-models">Generative Language Models</h3>
<ul>
<li>A language model can generate <strong>infinite outputs</strong> using a <strong>finite vocabulary</strong></li>
<li>Models capable of producing open-ended outputs are called <strong>generative models</strong></li>
<li>This forms the basis of <strong>Generative AI</strong></li>
</ul>
<hr>
</section>
</section>
<section id="learning-paradigms" class="level2">
<h2 class="anchored" data-anchor-id="learning-paradigms">Learning Paradigms</h2>
<section id="self-supervised-learning" class="level3">
<h3 class="anchored" data-anchor-id="self-supervised-learning">Self-Supervised Learning</h3>
<ul>
<li>Labels are automatically derived from the input data itself</li>
</ul>
</section>
<section id="unsupervised-learning" class="level3">
<h3 class="anchored" data-anchor-id="unsupervised-learning">Unsupervised Learning</h3>
<ul>
<li>No explicit labels are required</li>
</ul>
<hr>
</section>
</section>
<section id="when-to-outsource-model-building" class="level2">
<h2 class="anchored" data-anchor-id="when-to-outsource-model-building">When to Outsource Model Building</h2>
<section id="build-in-house-when" class="level3">
<h3 class="anchored" data-anchor-id="build-in-house-when">Build In-House When</h3>
<ul>
<li>The model is critical to business differentiation</li>
<li>There is a risk of exposing intellectual property to competitors</li>
</ul>
</section>
<section id="outsource-when" class="level3">
<h3 class="anchored" data-anchor-id="outsource-when">Outsource When</h3>
<ul>
<li>It improves productivity and profitability</li>
<li>It provides better performance and multiple vendor options</li>
</ul>
<hr>
</section>
</section>
<section id="role-of-ai-in-products" class="level2">
<h2 class="anchored" data-anchor-id="role-of-ai-in-products">Role of AI in Products</h2>
<section id="critical-vs-complementary" class="level3">
<h3 class="anchored" data-anchor-id="critical-vs-complementary">Critical vs Complementary</h3>
<ul>
<li><strong>Complementary:</strong><br>
The application can function without AI (e.g., Gmail)</li>
<li><strong>Critical:</strong><br>
The application cannot function without AI (e.g., face recognition)<br>
Requires high robustness and reliability</li>
</ul>
</section>
<section id="reactive-vs-proactive" class="level3">
<h3 class="anchored" data-anchor-id="reactive-vs-proactive">Reactive vs Proactive</h3>
<ul>
<li><strong>Reactive:</strong><br>
Responds to user inputs (e.g., chat-based responses)</li>
<li><strong>Proactive:</strong><br>
Takes initiative (e.g., traffic alerts in navigation apps)</li>
</ul>
</section>
<section id="static-vs-dynamic" class="level3">
<h3 class="anchored" data-anchor-id="static-vs-dynamic">Static vs Dynamic</h3>
<ul>
<li><strong>Static:</strong><br>
Features are updated only during application upgrades</li>
<li><strong>Dynamic:</strong><br>
Features evolve continuously based on user feedback</li>
</ul>
<hr>
</section>
</section>
<section id="automation-in-products-microsoft-framework" class="level2">
<h2 class="anchored" data-anchor-id="automation-in-products-microsoft-framework">Automation in Products (Microsoft Framework)</h2>
<ul>
<li><strong>Crawl:</strong><br>
Human involvement is required</li>
<li><strong>Walk:</strong><br>
AI assists and interacts with internal employees</li>
<li><strong>Run:</strong><br>
AI directly interacts with end users</li>
</ul>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Note</span>Key Insight
</div>
</div>
<div class="callout-body-container callout-body">
<p>Achieving <strong>0–60% performance is relatively easy</strong>, but moving from <strong>60–100% is extremely challenging</strong>.</p>
</div>
</div>
<hr>
</section>
<section id="three-layers-of-the-ai-stack" class="level2">
<h2 class="anchored" data-anchor-id="three-layers-of-the-ai-stack">Three Layers of the AI Stack</h2>
<section id="application-development-layer" class="level3">
<h3 class="anchored" data-anchor-id="application-development-layer">Application Development Layer</h3>
<ul>
<li>AI Interface</li>
<li>Prompt Engineering</li>
<li>Context Construction</li>
<li>Evaluation</li>
</ul>
</section>
<section id="model-development-layer" class="level3">
<h3 class="anchored" data-anchor-id="model-development-layer">Model Development Layer</h3>
<ul>
<li>Inference Optimization</li>
<li>Dataset Engineering</li>
<li>Modeling and Training</li>
<li>Evaluation</li>
</ul>
</section>
<section id="infrastructure-layer" class="level3">
<h3 class="anchored" data-anchor-id="infrastructure-layer">Infrastructure Layer</h3>
<ul>
<li>Compute Management</li>
<li>Data Management</li>
<li>Model Serving</li>
<li>Monitoring</li>
</ul>
<hr>
</section>
</section>
<section id="ai-engineering-vs-ml-engineering" class="level2">
<h2 class="anchored" data-anchor-id="ai-engineering-vs-ml-engineering">AI Engineering vs ML Engineering</h2>
<section id="ai-engineering" class="level3">
<h3 class="anchored" data-anchor-id="ai-engineering">AI Engineering</h3>
<ul>
<li>Uses pretrained models</li>
<li>Works with large-scale models</li>
<li>Requires higher compute resources</li>
<li>Workflow:<br>
<strong>Product → Data → Model</strong></li>
</ul>
</section>
<section id="ml-engineering" class="level3">
<h3 class="anchored" data-anchor-id="ml-engineering">ML Engineering</h3>
<ul>
<li>Trains models from scratch</li>
<li>Requires fewer resources</li>
<li>Workflow:<br>
<strong>Data → Model → Product</strong></li>
</ul>
<hr>
</section>
</section>
<section id="adapting-pretrained-models" class="level2">
<h2 class="anchored" data-anchor-id="adapting-pretrained-models">Adapting Pretrained Models</h2>
<ul>
<li><strong>Prompt Engineering</strong></li>
<li><strong>Fine-tuning</strong>
<ul>
<li>Training a pretrained model on a new task not seen during pretraining</li>
</ul></li>
</ul>
<hr>
</section>
<section id="training-stages" class="level2">
<h2 class="anchored" data-anchor-id="training-stages">Training Stages</h2>
<section id="pretraining" class="level3">
<h3 class="anchored" data-anchor-id="pretraining">Pretraining</h3>
<ul>
<li>Resource-intensive (large data and compute)</li>
<li>Model weights initialized randomly</li>
<li>Trained for general text completion</li>
</ul>
</section>
<section id="fine-tuning" class="level3">
<h3 class="anchored" data-anchor-id="fine-tuning">Fine-tuning</h3>
<ul>
<li>Requires significantly less data and compute</li>
<li>Adapts the model to task-specific objectives</li>
</ul>
</section>
<section id="post-training" class="level3">
<h3 class="anchored" data-anchor-id="post-training">Post-training</h3>
<ul>
<li>Often used interchangeably with fine-tuning</li>
<li><strong>Model developers:</strong><br>
Perform post-training before releasing the model (e.g., instruction-following)</li>
<li><strong>Application developers:</strong><br>
Fine-tune released models for specific downstream tasks</li>
</ul>
</section>
</section>
</section>
<section id="chapter-2-understanding-foundation-models" class="level1">
<h1>Chapter 2 Understanding Foundation Models</h1>
<section id="model-performance-fundamentals" class="level2">
<h2 class="anchored" data-anchor-id="model-performance-fundamentals">Model Performance Fundamentals</h2>
<ul>
<li>Model performance depends on both:
<ul>
<li><strong>Training process</strong></li>
<li><strong>Sampling (decoding) strategy</strong></li>
</ul></li>
<li>An AI model is only as good as the <strong>data it is trained on</strong></li>
<li>The <em>“use what we have, not what we want”</em> dataset mindset often leads to:
<ul>
<li>Strong performance on training data</li>
<li>Weak performance on real-world tasks</li>
</ul></li>
<li><strong>Small, high-quality datasets</strong> can outperform <strong>large, low-quality datasets</strong></li>
</ul>
<hr>
</section>
<section id="rnns-vs-transformers" class="level2">
<h2 class="anchored" data-anchor-id="rnns-vs-transformers">RNNs vs Transformers</h2>
<ul>
<li><strong>Recurrent Neural Networks (RNNs)</strong>
<ul>
<li>Generate text using a compressed <strong>summary of the book</strong></li>
<li>Struggle with long-range dependencies</li>
</ul></li>
<li><strong>Transformers</strong>
<ul>
<li>Attend directly to many tokens at once</li>
<li>Comparable to generating text using <strong>entire pages of a book</strong></li>
<li>Enable long-context modeling via attention</li>
</ul></li>
</ul>
<hr>
</section>
<section id="transformer-architecture" class="level2">
<h2 class="anchored" data-anchor-id="transformer-architecture">Transformer Architecture</h2>
<section id="transformer-block" class="level3">
<h3 class="anchored" data-anchor-id="transformer-block">Transformer Block</h3>
<p>Each transformer block consists of: - Attention module - MLP (feedforward network)</p>
</section>
<section id="transformer-based-language-model" class="level3">
<h3 class="anchored" data-anchor-id="transformer-based-language-model">Transformer-Based Language Model</h3>
<p>A typical transformer-based LM includes:</p>
<ul>
<li><strong>Embedding Module (pre-transformer)</strong>
<ul>
<li>Converts tokens into embedding vectors</li>
</ul></li>
<li><strong>Transformer Blocks</strong></li>
<li><strong>Model Head (post-transformer)</strong>
<ul>
<li>Converts hidden states into token probabilities</li>
</ul></li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/ai-engineering/weight_visualization.png" style="width:80%" class="figure-img">
<figcaption>
Figure 2.1: Visualization of the weight composition of a transformer model.
</figcaption>
</figure>
<hr>
</section>
</section>
<section id="alternatives-to-transformers" class="level2">
<h2 class="anchored" data-anchor-id="alternatives-to-transformers">Alternatives to Transformers</h2>
<ul>
<li><strong>RWKV</strong>
<ul>
<li>RNN-based architecture</li>
<li>No fixed context-length limitation</li>
<li>Performance on extremely long contexts is not guaranteed</li>
</ul></li>
<li><strong>State Space Models (SSMs)</strong>
<ul>
<li>Designed for long-range memory</li>
<li>Promising alternative to attention</li>
<li>Examples:
<ul>
<li>Mamba</li>
<li>Jamba (Hybrid of Transformer and Mamba)</li>
</ul></li>
</ul></li>
</ul>
<hr>
</section>
<section id="training-tokens-and-scaling-laws" class="level2">
<h2 class="anchored" data-anchor-id="training-tokens-and-scaling-laws">Training Tokens and Scaling Laws</h2>
<ul>
<li><p><img src="https://latex.codecogs.com/png.latex?%5Ctext%7BTotal%20Training%20Tokens%7D%20=%20%5Ctext%7BEpochs%7D%20%5Ctimes%20%5Ctext%7BTokens%20per%20epoch%7D"></p></li>
<li><p><strong>Chinchilla Scaling Law</strong></p>
<ul>
<li>Optimal training tokens ≈ <strong>20× model parameters</strong></li>
</ul></li>
<li><p>Research from Microsoft and OpenAI suggests:</p>
<ul>
<li>Hyperparameters can be transferred from a <strong>40M</strong> model to a <strong>6.7B</strong> model</li>
</ul></li>
</ul>
<hr>
</section>
<section id="pre-training-and-post-training" class="level2">
<h2 class="anchored" data-anchor-id="pre-training-and-post-training">Pre-training and Post-training</h2>
<ul>
<li><strong>Pre-training</strong>
<ul>
<li>Equivalent to <em>reading to acquire knowledge</em></li>
<li>Resource-intensive</li>
<li>Produces general-purpose representations</li>
</ul></li>
<li><strong>Post-training</strong>
<ul>
<li>Equivalent to <em>learning how to use knowledge</em></li>
<li>Includes instruction tuning, alignment, and RLHF</li>
</ul></li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/ai-engineering/traing_work_flow_of_llm.png" style="width:80%" class="figure-img">
<figcaption>
Figure 2.2: Training workflow of a large language model.
</figcaption>
</figure>
<ul>
<li>Training only on high-quality data without pre-training is possible, but <strong>pre-training followed by post-training yields superior results</strong></li>
</ul>
<hr>
</section>
<section id="reinforcement-learning-from-human-feedback-rlhf" class="level2">
<h2 class="anchored" data-anchor-id="reinforcement-learning-from-human-feedback-rlhf">Reinforcement Learning from Human Feedback (RLHF)</h2>
<p>RLHF is a two-stage process for aligning language models with human preferences:</p>
<ol type="1">
<li><strong>Train a reward model</strong> that scores the foundation model’s outputs</li>
<li><strong>Optimize the foundation model</strong> to generate responses that maximize the reward model’s score</li>
</ol>
<section id="preference-data-structure" class="level3">
<h3 class="anchored" data-anchor-id="preference-data-structure">Preference Data Structure</h3>
<p>Instead of using scalar scores (which vary across individuals), RLHF uses comparative preferences:</p>
<ul>
<li>Each training example consists of: <img src="https://latex.codecogs.com/png.latex?(prompt,%20winning%5C_response,%20losing%5C_response)"></li>
<li>This pairwise comparison approach captures relative quality more reliably than absolute ratings</li>
</ul>
</section>
<section id="reward-model-training" class="level3">
<h3 class="anchored" data-anchor-id="reward-model-training">Reward Model Training</h3>
<section id="objective" class="level4">
<h4 class="anchored" data-anchor-id="objective">Objective</h4>
<p>Maximize the score difference between winning and losing responses for each prompt.</p>
</section>
<section id="mathematical-formulation" class="level4">
<h4 class="anchored" data-anchor-id="mathematical-formulation">Mathematical Formulation</h4>
<p><strong>Notation:</strong></p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?r">: reward model</li>
<li><img src="https://latex.codecogs.com/png.latex?x">: prompt</li>
<li><img src="https://latex.codecogs.com/png.latex?y_w">: winning response</li>
<li><img src="https://latex.codecogs.com/png.latex?y_l">: losing response</li>
<li><img src="https://latex.codecogs.com/png.latex?s_w%20=%20r(x,%20y_w)">: reward score for winning response</li>
<li><img src="https://latex.codecogs.com/png.latex?s_l%20=%20r(x,%20y_l)">: reward score for losing response</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Csigma">: sigmoid function</li>
</ul>
<p><strong>Loss Function:</strong></p>
<p><img src="https://latex.codecogs.com/png.latex?%0A%5Cmathcal%7BL%7D%20=%20-%5Clog(%5Csigma(s_w%20-%20s_l))%0A"></p>
<p>where <img src="https://latex.codecogs.com/png.latex?%5Csigma(z)%20=%20%5Cfrac%7B1%7D%7B1%20+%20e%5E%7B-z%7D%7D"></p>
<p><strong>Goal:</strong> Minimize this loss function across all preference pairs</p>
</section>
<section id="model-architecture-choices" class="level4">
<h4 class="anchored" data-anchor-id="model-architecture-choices">Model Architecture Choices</h4>
<p>The reward model can be:</p>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Note</span>Reward Model Options
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li><strong>Trained from scratch</strong> on preference data</li>
<li><strong>Fine-tuned from a foundation model</strong> (often preferred, as the reward model should ideally match the capability level of the model being optimized)</li>
<li><strong>A smaller model</strong> (can also work effectively in practice, offering computational efficiency)</li>
</ul>
</div>
</div>
</section>
</section>
<section id="key-insights" class="level3">
<h3 class="anchored" data-anchor-id="key-insights">Key Insights</h3>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Tip</span>Important Takeaways
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>Pairwise preferences are more consistent and reliable than absolute ratings</li>
<li>The sigmoid in the loss function ensures the model learns relative differences in quality</li>
<li>The reward model’s capacity should generally align with the foundation model it’s evaluating</li>
</ul>
</div>
</div>
<hr>
</section>
</section>
<section id="sampling-strategies-and-model-hallucination" class="level2">
<h2 class="anchored" data-anchor-id="sampling-strategies-and-model-hallucination">Sampling Strategies and Model Hallucination</h2>
<section id="temperature-based-sampling" class="level3">
<h3 class="anchored" data-anchor-id="temperature-based-sampling">Temperature-Based Sampling</h3>
<section id="core-formula" class="level4">
<h4 class="anchored" data-anchor-id="core-formula">Core Formula</h4>
<p><img src="https://latex.codecogs.com/png.latex?%0AP(token)%20=%20%5Ctext%7Bsoftmax%7D%5Cleft(%5Cfrac%7B%5Ctext%7Blogits%7D%7D%7B%5Ctext%7Btemperature%7D%7D%5Cright)%0A"></p>
</section>
</section>
<section id="temperature-effects" class="level3">
<h3 class="anchored" data-anchor-id="temperature-effects">Temperature Effects</h3>
<ul>
<li><strong>Higher temperature</strong> reduces the probability of common tokens, thereby increasing the probability of rare tokens</li>
<li>This enables more <strong>creative and diverse responses</strong></li>
<li><strong>Standard value</strong>: Temperature of <strong>0.7</strong> balances creativity with coherent generation</li>
</ul>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Tip</span>Monitoring Model Learning
</div>
</div>
<div class="callout-body-container callout-body">
<p>To identify if a model is learning, examine the probability distributions. If probabilities remain random across training, the model is not learning effectively.</p>
</div>
</div>
</section>
<section id="numerical-stability" class="level3">
<h3 class="anchored" data-anchor-id="numerical-stability">Numerical Stability</h3>
<p>To avoid underflow issues (since probabilities can be extremely small), we use <strong>log probabilities</strong> in practice.</p>
</section>
</section>
<section id="advanced-sampling-strategies" class="level2">
<h2 class="anchored" data-anchor-id="advanced-sampling-strategies">Advanced Sampling Strategies</h2>
<section id="top-k-sampling" class="level3">
<h3 class="anchored" data-anchor-id="top-k-sampling">Top-k Sampling</h3>
<ul>
<li>Select the <strong>k largest logits</strong></li>
<li>Apply softmax only to these k tokens to compute probabilities</li>
<li><strong>Benefit</strong>: Reduces computational cost and filters out unlikely tokens</li>
</ul>
</section>
<section id="top-p-nucleus-sampling" class="level3">
<h3 class="anchored" data-anchor-id="top-p-nucleus-sampling">Top-p (Nucleus) Sampling</h3>
<ul>
<li>Find the <strong>smallest set of tokens</strong> whose cumulative probabilities sum to <img src="https://latex.codecogs.com/png.latex?p"></li>
<li><strong>Process</strong>: Sort tokens by probability (descending order) and keep adding until cumulative probability reaches <img src="https://latex.codecogs.com/png.latex?p"></li>
<li>More adaptive than top-k as the number of considered tokens varies</li>
</ul>
</section>
<section id="min-p-sampling" class="level3">
<h3 class="anchored" data-anchor-id="min-p-sampling">Min-p Sampling</h3>
<ul>
<li>Set a <strong>minimum probability threshold</strong> for tokens to be considered</li>
<li>Any token with probability below this threshold is excluded from sampling</li>
</ul>
</section>
<section id="best-of-n-sampling" class="level3">
<h3 class="anchored" data-anchor-id="best-of-n-sampling">Best-of-N Sampling</h3>
<ul>
<li>Generate <strong>multiple responses</strong> for the same prompt</li>
<li>Select the response with the <strong>maximum average probability</strong></li>
<li>Improves output quality at the cost of increased compute</li>
</ul>
</section>
</section>
<section id="handling-structured-outputs" class="level2">
<h2 class="anchored" data-anchor-id="handling-structured-outputs">Handling Structured Outputs</h2>
<section id="prompting-techniques" class="level3">
<h3 class="anchored" data-anchor-id="prompting-techniques">1. Prompting Techniques</h3>
<ul>
<li><strong>Better prompt engineering</strong> with clear instructions</li>
<li><strong>Two-query approach</strong>:
<ul>
<li>First query generates the response</li>
<li>Second query validates the response format</li>
</ul></li>
</ul>
</section>
<section id="post-processing" class="level3">
<h3 class="anchored" data-anchor-id="post-processing">2. Post-Processing</h3>
<ul>
<li>Identify <strong>repeated common mistakes</strong> in model outputs</li>
<li>Write scripts to correct these systematic errors</li>
<li>Works well when the model produces mostly correct formats with predictable issues</li>
</ul>
</section>
<section id="constrained-sampling" class="level3">
<h3 class="anchored" data-anchor-id="constrained-sampling">3. Constrained Sampling</h3>
<ul>
<li>Sample only from a <strong>selected set of valid tokens</strong></li>
<li><strong>Example</strong>: In JSON generation, prevent invalid syntax like <code>{{</code> without an intervening key</li>
<li>Enforces grammatical/syntactic correctness at the token level</li>
</ul>
</section>
<section id="test-time-compute" class="level3">
<h3 class="anchored" data-anchor-id="test-time-compute">4. Test-Time Compute</h3>
<ul>
<li>Generate multiple candidate responses</li>
<li>Use a selection mechanism to output the best one</li>
<li>Trade compute for quality</li>
</ul>
</section>
<section id="fine-tuning-1" class="level3">
<h3 class="anchored" data-anchor-id="fine-tuning-1">5. Fine-Tuning</h3>
<div class="callout callout-style-default callout-important callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Important</span>Best Solution
</div>
</div>
<div class="callout-body-container callout-body">
<p>Fine-tuning is the most effective approach for structured outputs:</p>
<ul>
<li><strong>Full model fine-tuning</strong> (better if resources available)</li>
<li><strong>Partial fine-tuning</strong> (LoRA, adapters, etc.)</li>
<li>Directly teaches the model the desired output format</li>
</ul>
</div>
</div>
</section>
</section>
<section id="model-hallucination" class="level2">
<h2 class="anchored" data-anchor-id="model-hallucination">Model Hallucination</h2>
<section id="definition" class="level3">
<h3 class="anchored" data-anchor-id="definition">Definition</h3>
<p><strong>Hallucination</strong> occurs when a model generates responses that are <strong>not grounded in factual information</strong>.</p>
</section>
<section id="consistency-issues" class="level3">
<h3 class="anchored" data-anchor-id="consistency-issues">Consistency Issues</h3>
<p>Due to the <strong>probabilistic nature</strong> of language models:</p>
<ul>
<li>Same prompt can produce <strong>multiple different outputs</strong></li>
<li>This inconsistency can be problematic for production systems</li>
</ul>
<section id="mitigation-strategies" class="level4">
<h4 class="anchored" data-anchor-id="mitigation-strategies">Mitigation Strategies</h4>
<ol type="1">
<li><strong>Caching</strong>: Store responses for repeated queries to ensure consistency</li>
<li><strong>Sampling adjustments</strong>: Modify temperature, top-k, or top-p parameters</li>
<li><strong>Deterministic seeds</strong>: Use fixed random seeds</li>
</ol>
<div class="callout callout-style-default callout-warning callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Warning</span>No Perfect Solution
</div>
</div>
<div class="callout-body-container callout-body">
<p>Even with these techniques, <strong>100% consistency is not guaranteed</strong>. Hardware differences in floating-point computation can lead to variations across different systems.</p>
</div>
</div>
</section>
</section>
</section>
<section id="why-models-hallucinate" class="level2">
<h2 class="anchored" data-anchor-id="why-models-hallucinate">Why Models Hallucinate</h2>
<section id="hypothesis-1-self-supervision-is-the-culprit" class="level3">
<h3 class="anchored" data-anchor-id="hypothesis-1-self-supervision-is-the-culprit">Hypothesis 1: Self-Supervision is the Culprit</h3>
<p><strong>Problem</strong>: Models cannot differentiate between:</p>
<ul>
<li><strong>Given data</strong> (the prompt)</li>
<li><strong>Generated data</strong> (their own outputs)</li>
</ul>
<section id="example-scenario" class="level4">
<h4 class="anchored" data-anchor-id="example-scenario">Example Scenario</h4>
<ol type="1">
<li><strong>Prompt</strong>: “Who is Chip Huyen?”</li>
<li><strong>Model generates</strong>: “Chip Huyen is an architect”</li>
<li><strong>Next token generation</strong>: The model treats “Chip Huyen is an architect” as a fact, just like the original prompt</li>
<li><strong>Consequence</strong>: If the initial generation is incorrect, the model will continue to justify and build upon the incorrect information</li>
</ol>
</section>
<section id="mitigation-techniques" class="level4">
<h4 class="anchored" data-anchor-id="mitigation-techniques">Mitigation Techniques</h4>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Note</span>Approach 1: Reinforcement Learning
</div>
</div>
<div class="callout-body-container callout-body">
<p>From RL perspective, train the model to differentiate between:</p>
<ul>
<li><strong>Observations about the world</strong> (given text/prompt)</li>
<li><strong>Model’s actions</strong> (generated text)</li>
</ul>
<p>This helps the model maintain awareness of what is given vs.&nbsp;what it produces.</p>
</div>
</div>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Note</span>Approach 2: Supervised Fine-Tuning with Counterfactuals
</div>
</div>
<div class="callout-body-container callout-body">
<p>Include both <strong>factual</strong> and <strong>counterfactual</strong> examples in training data, explicitly teaching the model to recognize and avoid false information.</p>
</div>
</div>
</section>
</section>
<section id="hypothesis-2-supervision-is-the-culprit" class="level3">
<h3 class="anchored" data-anchor-id="hypothesis-2-supervision-is-the-culprit">Hypothesis 2: Supervision is the Culprit</h3>
<p><strong>Problem</strong>: Conflict between the model’s internal knowledge and labeler knowledge during SFT (Supervised Fine-Tuning).</p>
<section id="the-issue" class="level4">
<h4 class="anchored" data-anchor-id="the-issue">The Issue</h4>
<ul>
<li>During SFT, models are trained on responses written by <strong>human labelers</strong></li>
<li>Labelers use their own knowledge to write responses</li>
<li>The <strong>model may not have access</strong> to the same knowledge base</li>
<li>Result: The model learns to produce responses it cannot properly ground, leading to hallucination</li>
</ul>
</section>
<section id="better-approach" class="level4">
<h4 class="anchored" data-anchor-id="better-approach">Better Approach</h4>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Tip</span>Solution: Include Reasoning Chains
</div>
</div>
<div class="callout-body-container callout-body">
<p>When creating training data:</p>
<ol type="1">
<li><strong>Document the information sources</strong> used to arrive at the response</li>
<li><strong>Include reasoning steps</strong> that show how the conclusion was reached</li>
<li>This allows the model to understand <strong>not just what to say</strong>, but <strong>why</strong> and <strong>based on what information</strong></li>
</ol>
</div>
</div>
</section>
</section>
</section>
</section>
<section id="chapter-3-evaluation-methodology" class="level1">
<h1>Chapter 3 Evaluation Methodology</h1>
<section id="challenges-of-evaluating-foundation-models" class="level2">
<h2 class="anchored" data-anchor-id="challenges-of-evaluating-foundation-models">Challenges of Evaluating Foundation Models</h2>
<ul>
<li><p>As AI becomes more intelligent, it is hard to evaluate them. Most people can evalaute the 1st grade maths but not phd level</p></li>
<li><p>There are so many possibilities for a single query since foundation models are open-ended not like ML classification models, where it is wrong if predicts y instead of x</p></li>
<li><p>For most of the models, their architecture, training data, training processes are not exposed, so we dont know whether we are evaulating it on wrng task or not</p></li>
<li><p>Evaluation is not about only assessing the model’s performance on specific task, it also helps in finding out the potenital and limitations of foundation model</p></li>
</ul>
</section>
<section id="language-modeling-metrics" class="level2">
<h2 class="anchored" data-anchor-id="language-modeling-metrics">Language Modeling Metrics</h2>
<ul>
<li>Entropy:- is how much information a token carries, Higher the entropy more info and more bits are needed to represent
<ul>
<li>Consider two languages one with 2 tokens and other with 4 tokens, both have 1 and 2 entropy respetively. thus making hardr for prediction whn entropy is 4</li>
<li>Entropy is basically how hard it is to predict next token</li>
</ul></li>
<li>Cross Entropy:- how much difficult it is to predict next token by a language model on a dataset</li>
<li>A language model is trained to minimize its cross entropy with respect to training data
<ul>
<li>H(P, Q) = H(P) + Dkl(P||Q)</li>
<li>where H(P, Q) is entropy of P(true distribtuion) with respect to Q(distribution learned by model)</li>
<li>while traing a language model, we want to minimize this</li>
</ul></li>
<li>Bits-per-character and Bits-per-byte
<ul>
<li>BPC:- bits required to represent a token, eg. if a tokenizer takes 6 bits to represnt a token and token have 2 chars then BPC is 3</li>
<li>Since there can be multiple encoding schemes[ASCII(7 bits), UTF-8(8-32bits)], bits-per-character will differ</li>
<li>BPB:- bits a language model need to represent 1 byte of training data
<ul>
<li>lets say BPC is 3 of the trained model and 7 bits are required to represent a single character of training datta then we can say that
<ul>
<li>7 bit of data is beng represnted using 3 bit</li>
<li>1 bit of data is being represented using 3/7 bits</li>
<li>so for 1 byte i.e.&nbsp;8bit it is 24/7</li>
<li>it simply means that 3.43 bits are needed by model to represnt 1 byte of training data</li>
</ul></li>
</ul></li>
</ul></li>
<li>Perplexity
<ul>
<li>It is the exponential of entropy and cross entropy</li>
<li>PPL(P) = 2^H(P)</li>
<li>PPL(P, Q) = 2^H(P, Q)</li>
<li>If cross entropy measures how difficult it is to pedict next token then ppl defines how uncertain it for predicting the next token, i.e.&nbsp;higher the ppl more will be options</li>
<li>If base 2 then bits and if base is e then nat</li>
</ul></li>
<li>Perplexity Interpretation and Use Cases
<ul>
<li>More structured data gives lower PPL. HTML will have lower PPL compared to everyday text since after <code>&lt;head&gt;</code> there will always be <code>&lt;/head&gt;</code>.</li>
<li>The bigger the vocabulary, the higher the PPL since there will be lot of the options for predicting</li>
<li>The longer the cntext length, the less will be PPL i.e if a model have more context then it will have less uncertainty in predicting next token</li>
<li>PPL can be used to identify if the model was trained on given dataset or not, since if the model has seen the data in training time then it will have lower PPL otherwise higher PPL</li>
</ul></li>
<li>Post-training techniques like SFT or RLHF may lead to increase in PPL, since they gets modified for completion task from next token prediction</li>
<li>Formula to calculate PPL given n tokens</li>
</ul>
</section>
<section id="exact-evaluation" class="level2">
<h2 class="anchored" data-anchor-id="exact-evaluation">Exact Evaluation</h2>
<ul>
<li>Functional Correcteness
<ul>
<li>Whether the model is generating the intended texts or not e.g.&nbsp;if asked to create a website whether the created website is as intended or not</li>
<li>Functional correctness of codes can be automated easily by passing the genertaed code to a particular interpreter to check if the ouput from the generated code is same as the expected one or not</li>
<li>pass<code>@k</code> x%:- fraction of passed sample cases at generation number k</li>
</ul></li>
<li>Similarity measurements against reference data
<ul>
<li>Generated responses that are more similar to the reference responses are considered to be better</li>
<li>There are 4 ways to measure similarity between two open-ended texts:-
<ul>
<li>Ask an evaluator, whether the two texts are same or not</li>
<li>Exact match: Does generated response matches exactly with one of the reference responses</li>
<li>Lexical similarity: How similar generated response looks to the refernce response</li>
<li>Semantic Similarity: How close they are semantically in meaning</li>
</ul></li>
<li>Exact Match:-
<ul>
<li>When we hvae to generate short answers or deterministic ouputs.</li>
<li>It gives output either 1 or 0</li>
<li>2+3=?. If genertaed response is 5 or “The answer is 5” is acceptable</li>
<li>If the input was “Birthday of XYZ” and if it gives correct year but not date then it is considered wrong</li>
<li>but in case of translation there might be multiple sequence possible for a given text</li>
</ul></li>
<li>Lexical Similarity:-
<ul>
<li>One way is to count the number of tokens which are in common [can be increased to n-gram tokens instead of comparing 1 token (what percentage of reference responses is also in the generated responses)]</li>
<li>Use some fuzzy logic i.e.&nbsp;edit distance [insert, delete substitute] to check how much edits are need to get the same text</li>
<li>Common metrices are BLEU, ROUGE, METEOR++, TER, CIDEr</li>
<li>Some cons are that:-
<ul>
<li>we have to curate all the possible reference data samples.</li>
<li>It is also possible that the model generates a good quality text and gets lower score because the generated text was not found in refernce data</li>
<li>It is also possible that refernce data is wrong, so reference based evaluations are not good considering refernce free ones</li>
<li>Also it is not possible to blindly trust this metric. eg. on some code benchmark BLUE score was same for incorrect as well as correct ouputs</li>
</ul></li>
</ul></li>
<li>Semantic Similarity:-
<ul>
<li>It calculates the similarity in semantics by converting given texts in to embedding</li>
<li>Cosine similarity is used to find out the similarity</li>
<li>1 if they are almost similar, -1 if they are completely opposite</li>
<li>This is under exact match, because embedding generation algo might differ but calculation of semnatic similary will be same</li>
<li>Metric for semantic textual similarity
<ul>
<li>BERTScore:- Embeddings are generated by BERT</li>
<li>MoverScore:- Embeddings are generated by mixture of algorithms</li>
</ul></li>
<li>Cons is that what if embeding generation module is not perfect then even if two texts are semantical same, it will say otherwise and there is an overhead of compuatation of embedding</li>
</ul></li>
</ul></li>
<li>Benchmark that measures the embedding quality on various tasks is MTEB[Massive Text Embedding Benchmark]</li>
</ul>
</section>
<section id="ai-as-a-judge" class="level2">
<h2 class="anchored" data-anchor-id="ai-as-a-judge">AI as a Judge</h2>
<ul>
<li><p>AI judges are cheap in comparison of humans</p></li>
<li><p>There are three ways you can use AI to evaluate:-</p>
<ul>
<li>Using the AI itslef which generated the response</li>
<li>Using AI to compare against a given refernce data</li>
<li>Using another response</li>
</ul></li>
<li><p>Use discrete scoring, less the options for scoring better will be the evaluation by AI</p></li>
<li><p>Evaluation can also be made better by giving the possible examples for each category or score</p></li>
<li><p>Limitations:</p>
<ul>
<li>Inconsistency:- Since they are probabilistic, they will give different output for the same prompt</li>
<li>Criteria-Ambiguity:- Some AI evaluators give yes no, some give 1-5 or 1-2. What is the evaluator changed or the prompt used was changed</li>
<li>Increased Cost &amp; Latency:- Using AI evaluations can add upto to inference cost as well as add latency to the whole pipeline</li>
<li>Biases of AI as a judge:- AI evalators tend to prefer their reponses over the responses generated other models even it is not correct
<ul>
<li>first postion bias as they tend to prefer first option as opposite of humans, where they prefer last option</li>
<li>verbosity bias is favouring lengthier outputs even if it is wrong</li>
</ul></li>
</ul></li>
</ul>
</section>
<section id="what-models-can-act-as-a-judge" class="level2">
<h2 class="anchored" data-anchor-id="what-models-can-act-as-a-judge">What models can act as a Judge?</h2>
<ul>
<li>Strong Model as Judge
<ul>
<li>Evaluate a subset of responses generated by a stronger model</li>
</ul></li>
<li>Same model as Judge
<ul>
<li>It is like cheating, but it would help in sanity check that if the model itself thnks the output is not correct then the model itself is not good</li>
</ul></li>
<li>Weaker model as judge
<ul>
<li>Since judging is easier than generating a response</li>
</ul></li>
<li>Specialised AI Judges
<ul>
<li>Reward model:- Given a pair of prompt and response, it gives a score of how good response is</li>
<li>Refrence based Judge:- Evaluate similarity score or quality against given refernce responses</li>
<li>Preference Model:- Given multiple response for a prompt, they provide ranking</li>
</ul></li>
</ul>
</section>
<section id="ranking-models-with-comparative-evaluation" class="level2">
<h2 class="anchored" data-anchor-id="ranking-models-with-comparative-evaluation">Ranking Models with Comparative Evaluation</h2>
<ul>
<li>We evaluate models, not because we want to check their scores but to find out which one is better for our use case</li>
<li>Pointwise Evaluation is evaluating each model independenlty and then comapring their scores</li>
<li>Comaparative Evaluation is evaluating models against each other and then ranking them from comparative results. For e.g.&nbsp;asking the participants to dance simultaneusly and then judge them</li>
<li>Comparative evaluation is better since we have to compare responses instead of giving score to each response</li>
<li>One think to note is that responses can not be calculated solely based on preference for example there are some questions which needs to be judged by correctness</li>
<li>Also giving two responses for a math problem and then asking the user to give the prefernce score. If user know about that problem then why would he had asked about it</li>
<li>Basically for a preference based voting only works when voters are knowledgeable in the subject</li>
<li>There is a difference between A/B testing and comparative evaluation
<ul>
<li>in A/B testing we use same model to get the outputs</li>
<li>in comparative evaluation, we use different models for same input to get different outputs</li>
</ul></li>
</ul>
</section>
<section id="challeneges-of-comparative-evaluation" class="level2">
<h2 class="anchored" data-anchor-id="challeneges-of-comparative-evaluation">Challeneges of Comparative Evaluation</h2>
<ul>
<li>Scalibility Bottleneck:- Comparartive Evaluations are data intensive. Whenever a new model comes in we have to evaluate it against existing ones which will change the ranking. There is also no clearity on transitivity if A better than B and B is better than C then it does not imply that A is better than C. To mititgate these issues, we can design a matching algorithm which will help try to distinguish when there is more confusion between two models rather than evaluation two models which are already far from each other in performance</li>
<li>Lack of standardization and quality control:- There is not a standard way to evaluate. Someone on internet might prefer facts instead of gramaically, some might prefer toxic contents which is good and bad also. There is also lack of prompts to evaluate for example there might be 305</li>
</ul>


</section>
</section>

 ]]></description>
  <category>Books</category>
  <guid>https://riteshrm.github.io/posts/ai-engineering/</guid>
  <pubDate>Tue, 13 Jan 2026 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/ai-engineering/resized_thumbnail.png" medium="image" type="image/png" height="82" width="144"/>
</item>
<item>
  <title>Attention Mechanism</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/attention-mechanism/</link>
  <description><![CDATA[ 





<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
<span class="screen-reader-only">Tip</span>References
</div>
</div>
<div class="callout-body-container callout-body">
<ul>
<li>This is mostly based on:
<ol type="1">
<li><a href="https://arxiv.org/abs/1706.03762">Attention Is All You Need</a></li>
<li><a href="https://arxiv.org/abs/2006.16236">Transformers are RNNs: Fast Autoregressive Transformers with Linear Attention</a></li>
</ol></li>
</ul>
</div>
</div>
<hr>
<section id="motivation" class="level2">
<h2 class="anchored" data-anchor-id="motivation">Motivation</h2>
<section id="issue-with-rnns" class="level3">
<h3 class="anchored" data-anchor-id="issue-with-rnns">Issue with RNNs</h3>
<ul>
<li>Information Bottleneck:- If sentence is too much long, they needed to compress all the previous token information in just a single vector h</li>
<li>Sequential Nature:- All the tokens being processed one by one</li>
</ul>
</section>
<section id="quotient-rule" class="level3">
<h3 class="anchored" data-anchor-id="quotient-rule">Quotient rule</h3>
<ul>
<li>Will be used while finding out the derivative of softmax</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cleft(%5Cfrac%7Bu%7D%7Bv%7D%5Cright)'%20=%20%5Cfrac%7Bu'v%20-%20uv'%7D%7Bv%5E2%7D">.</li>
</ul>
</section>
</section>
<section id="scaled-dot-product-attention" class="level2">
<h2 class="anchored" data-anchor-id="scaled-dot-product-attention">Scaled Dot-Product Attention</h2>
<section id="transformers" class="level3">
<h3 class="anchored" data-anchor-id="transformers">Transformers</h3>
<ul>
<li>Given a sequence of length N, where each token is represented by d_model numbers, we compute three matrices
<ul>
<li><img src="https://latex.codecogs.com/png.latex?Query%20=%20XW_q"> (what I’m looking for)</li>
<li><img src="https://latex.codecogs.com/png.latex?Key%20=%20XW_k"> (what I have)</li>
<li><img src="https://latex.codecogs.com/png.latex?Value%20=%20XW_v"> (the information I’ll give if I’m relevant)</li>
<li><img src="https://latex.codecogs.com/png.latex?W_q"> and <img src="https://latex.codecogs.com/png.latex?W_k"> are of same shape and to maintain the symmetry <img src="https://latex.codecogs.com/png.latex?W_v"> is also kept to be of same shape, <img src="https://latex.codecogs.com/png.latex?W_q">, <img src="https://latex.codecogs.com/png.latex?W_k"> [<img src="https://latex.codecogs.com/png.latex?d_%7Bmodel%7D">, <img src="https://latex.codecogs.com/png.latex?d_k">] and <img src="https://latex.codecogs.com/png.latex?W_v"> [<img src="https://latex.codecogs.com/png.latex?d_%7Bmodel%7D">, <img src="https://latex.codecogs.com/png.latex?d_k">]</li>
</ul></li>
<li>Now to find out which key is more relevant to given queries we do matrix multiplication and the finally apply softmax to get probability
<ul>
<li>score = <img src="https://latex.codecogs.com/png.latex?QueryKey%5ET"></li>
<li>attn = <img src="https://latex.codecogs.com/png.latex?softmax(%5Cfrac%7Bscore%7D%7B%5Csqrt%7Bd_k%7D%7D)"></li>
<li>Why scaling factor
<ul>
<li>this score dot product has variance of d_k, which causes instability in backpropagation
<ul>
<li>let’s say we have two vectors q and k of dimension d_k</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D%5Bq_i%5D%20%20=%20%5Cmathbb%7BE%7D%5Bk_i%5D%20=%200"></li>
<li><img src="https://latex.codecogs.com/png.latex?var%5Bq_i%5D=var%5Bk_i%5D%20=%201"></li>
<li>then <img src="https://latex.codecogs.com/png.latex?%5Cmathbb%7BE%7D%5Bq.k%5D%20=%200"> but <img src="https://latex.codecogs.com/png.latex?var%5Bq.k%5D%20=%20d_k"> <a href="https://funnywii.com/upload/proof.pdf">link</a></li>
</ul></li>
<li>the derivative of softmax contains some terms which if not normalized lead to gradient nearly 0 because of this larger variance</li>
<li><img src="https://latex.codecogs.com/png.latex?%5Ctext%7BSoftmax%7D(z_i)%20=%20%5Cfrac%7Be%5E%7Bz_i%7D%7D%7B%5Csum_j%20e%5E%7Bz_j%7D%7D"></li>
<li><img src="https://latex.codecogs.com/png.latex?%5Cfrac%7B%5Cpartial%20%5Ctext%7BSoftmax%7D(z)_i%7D%7B%5Cpartial%20z_j%7D%20=%20%5Ctext%7BSoftmax%7D(z)_i%20(%5Cdelta_%7Bij%7D%20-%20%5Ctext%7BSoftmax%7D(z)_j)"></li>
<li>If <img src="https://latex.codecogs.com/png.latex?z_i"> is much larger than other elements, <img src="https://latex.codecogs.com/png.latex?%5Ctext%7BSoftmax%7D(z)_i%20%5Capprox%201">.</li>
<li>If <img src="https://latex.codecogs.com/png.latex?z_i"> is much smaller, <img src="https://latex.codecogs.com/png.latex?%5Ctext%7BSoftmax%7D(z)_i%20%5Capprox%200">.</li>
<li>So in case of jacobian matrix, considering a simple case where query 0 attends all the keys
<ul>
<li>Diagonal: <img src="https://latex.codecogs.com/png.latex?s_1(1-s_1)%20%5Capprox%201(0)%20=%200">.</li>
<li>Off-Diagonal: <img src="https://latex.codecogs.com/png.latex?-s_1%20s_2%20%5Capprox%20-1(0)%20=%200">.</li>
</ul></li>
<li>to enforce unit variance, we apply normalization by dividing the score by standard deviation i.e.&nbsp;<img src="https://latex.codecogs.com/png.latex?%5Csqrt%7Bd_k%7D"></li>
</ul></li>
</ul></li>
</ul>
<div class="callout callout-style-default callout-note callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Note
</div>
</div>
<div class="callout-body-container callout-body">
<p>The scaling factor keeps the variance of the dot-product scores controlled as <img src="https://latex.codecogs.com/png.latex?d_k"> grows, which helps avoid softmax saturation and near-zero gradients.</p>
</div>
</div>
</section>
</section>
<section id="pytorch-implementations" class="level2">
<h2 class="anchored" data-anchor-id="pytorch-implementations">PyTorch Implementations</h2>
<section id="single-head-vanilla-attention-pytorch-code" class="level3">
<h3 class="anchored" data-anchor-id="single-head-vanilla-attention-pytorch-code">Single Head Vanilla Attention PyTorch Code</h3>
<div id="ddae75af" class="cell" data-execution_count="1">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb1" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb1-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb1-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb1-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb1-4"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> time</span>
<span id="cb1-5"></span>
<span id="cb1-6">device <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.device(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"cuda"</span> <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> torch.cuda.is_available() <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span> <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"cpu"</span>)</span>
<span id="cb1-7"></span>
<span id="cb1-8"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> SingleHeadVanillaAttention(nn.Module):</span>
<span id="cb1-9">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, d_model, d_k):</span>
<span id="cb1-10">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb1-11">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model</span>
<span id="cb1-12">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_k</span>
<span id="cb1-13">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wq <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k)</span>
<span id="cb1-14">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wk <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k)</span>
<span id="cb1-15">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wv <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k)</span>
<span id="cb1-16"></span>
<span id="cb1-17">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> forward(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x):</span>
<span id="cb1-18">        query <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wq(x) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb1-19">        key <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wk(x)   <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">#[B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb1-20">        value <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wv(x) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb1-21"></span>
<span id="cb1-22">        scores <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.matmul(query, key.transpose(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span>) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k] * [B, d_k, N] -&gt; [B, N, N] TC=O(B*N^2*d_k)</span></span>
<span id="cb1-23"></span>
<span id="cb1-24">        attn <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> F.softmax(scores, dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, N]</span></span>
<span id="cb1-25"></span>
<span id="cb1-26">        final <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.matmul(attn, value) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, N] * [B, N, d_k] -&gt; [B, N, d_k]  TC=O(B*N^2*d_k)</span></span>
<span id="cb1-27">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> final <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k]</span></span>
<span id="cb1-28"></span>
<span id="cb1-29">d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb1-30">d_k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb1-31"></span>
<span id="cb1-32">model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> SingleHeadVanillaAttention(d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model, d_k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_k).requires_grad_(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">eval</span>().to(device)</span>
<span id="cb1-33"></span>
<span id="cb1-34">n_tokens <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">16384</span></span>
<span id="cb1-35">inp <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, n_tokens, d_model, device<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>device)</span>
<span id="cb1-36"></span>
<span id="cb1-37">torch.cuda.synchronize()</span>
<span id="cb1-38">start <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> time.time()</span>
<span id="cb1-39">k<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">50</span></span>
<span id="cb1-40"><span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> _ <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(k):</span>
<span id="cb1-41">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">with</span> torch.no_grad():</span>
<span id="cb1-42">        out <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> model(inp)</span>
<span id="cb1-43">torch.cuda.synchronize()</span>
<span id="cb1-44"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">f"Time taken: </span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span>(time.time()<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>start)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>k<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">:.3f}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>)</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<pre><code>Time taken: 0.508</code></pre>
</div>
</div>
</section>
<section id="multi-head-vanilla-attention-for-loop-pytorch-code" class="level3">
<h3 class="anchored" data-anchor-id="multi-head-vanilla-attention-for-loop-pytorch-code">Multi Head Vanilla Attention For loop PyTorch Code</h3>
<div id="f7beaebf" class="cell" data-execution_count="2">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb3" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb3-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb3-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb3-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb3-4"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> time</span>
<span id="cb3-5"></span>
<span id="cb3-6">device <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.device(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"cuda"</span> <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> torch.cuda.is_available() <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span> <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"cpu"</span>)</span>
<span id="cb3-7"></span>
<span id="cb3-8"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> MultiHeadVanillaAttention(nn.Module):</span>
<span id="cb3-9">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, d_model, num_heads, head_dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>):</span>
<span id="cb3-10">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb3-11">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model</span>
<span id="cb3-12">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> num_heads</span>
<span id="cb3-13">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> head_dim <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>:</span>
<span id="cb3-14">            <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads</span>
<span id="cb3-15">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span>:</span>
<span id="cb3-16">            <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> head_dim</span>
<span id="cb3-17">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wq <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.ModuleList([nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> _ <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads)])</span>
<span id="cb3-18">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wk <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.ModuleList([nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> _ <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads)])</span>
<span id="cb3-19">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wv <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.ModuleList([nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> _ <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads)])</span>
<span id="cb3-20">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.out <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model)</span>
<span id="cb3-21"></span>
<span id="cb3-22">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> forward(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x):</span>
<span id="cb3-23">        query <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wq[i](x) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads)] <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb3-24">        key <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wk[i](x) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads)]   <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">#[B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb3-25">        value <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wv[i](x) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads)] <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb3-26"></span>
<span id="cb3-27">        scores <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [torch.matmul(query[i], key[i].transpose(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span>) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads)] <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k] * [B, d_k, N] -&gt; [B, N, N] TC=O(B*N^2*d_k)</span></span>
<span id="cb3-28"></span>
<span id="cb3-29">        attn <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [F.softmax(scores[i], dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads)] <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, N]</span></span>
<span id="cb3-30"></span>
<span id="cb3-31">        final <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [torch.matmul(attn[i], value[i]) <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads)] <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, N] * [B, N, d_k] -&gt; [B, N, d_k]  TC=O(B*N^2*d_k)</span></span>
<span id="cb3-32">        final <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.cat(final, dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb3-33"></span>
<span id="cb3-34">        projout <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.out(final)</span>
<span id="cb3-35"></span>
<span id="cb3-36">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> projout <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_model]</span></span>
<span id="cb3-37"></span>
<span id="cb3-38">d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb3-39">d_k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb3-40"></span>
<span id="cb3-41">model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> MultiHeadVanillaAttention(d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model, num_heads<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, head_dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">32</span>).requires_grad_(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">eval</span>().to(device)</span>
<span id="cb3-42"></span>
<span id="cb3-43">n_tokens <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">16384</span></span>
<span id="cb3-44">inp <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, n_tokens, d_model, device<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>device)</span>
<span id="cb3-45"></span>
<span id="cb3-46">torch.cuda.synchronize()</span>
<span id="cb3-47">start <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> time.time()</span>
<span id="cb3-48">k<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">50</span></span>
<span id="cb3-49"><span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> _ <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(k):</span>
<span id="cb3-50">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">with</span> torch.no_grad():</span>
<span id="cb3-51">        out <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> model(inp)</span>
<span id="cb3-52">torch.cuda.synchronize()</span>
<span id="cb3-53"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">f"Time taken: </span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span>(time.time()<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>start)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>k<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">:.3f}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>)</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<pre><code>Time taken: 0.926</code></pre>
</div>
</div>
</section>
<section id="multi-head-vanilla-attention-pytorch-code" class="level3">
<h3 class="anchored" data-anchor-id="multi-head-vanilla-attention-pytorch-code">Multi Head Vanilla Attention PyTorch Code</h3>
<div id="9e54e867" class="cell" data-execution_count="3">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb5" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb5-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb5-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb5-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb5-4"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> time</span>
<span id="cb5-5"></span>
<span id="cb5-6">device <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.device(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"cuda"</span> <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> torch.cuda.is_available() <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span> <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"cpu"</span>)</span>
<span id="cb5-7"></span>
<span id="cb5-8"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> MultiHeadVanillaAttention(nn.Module):</span>
<span id="cb5-9">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, d_model, head_dim, num_heads):</span>
<span id="cb5-10">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb5-11">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model</span>
<span id="cb5-12">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> head_dim <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> num_heads</span>
<span id="cb5-13">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.head_dim <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> head_dim</span>
<span id="cb5-14">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> num_heads</span>
<span id="cb5-15">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wq <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k)</span>
<span id="cb5-16">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wk <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k)</span>
<span id="cb5-17">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wv <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k)</span>
<span id="cb5-18"></span>
<span id="cb5-19">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.out <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_model)</span>
<span id="cb5-20">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> forward(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x):</span>
<span id="cb5-21">        batch_size <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> x.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>]</span>
<span id="cb5-22">        query <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wq(x) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb5-23">        key <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wk(x)   <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">#[B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb5-24">        value <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wv(x) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb5-25"></span>
<span id="cb5-26">        query <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> query.view(batch_size, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.head_dim).transpose(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k] -&gt; [B, N, num_heads, head_dim] -&gt; [B, num_heads, N, head_dim]</span></span>
<span id="cb5-27">        key <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> key.view(batch_size, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.head_dim).transpose(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k] -&gt; [B, N, num_heads, head_dim] -&gt; [B, num_heads, N, head_dim]</span></span>
<span id="cb5-28">        value <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> value.view(batch_size, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.num_heads, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.head_dim).transpose(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k] -&gt; [B, N, num_heads, head_dim] -&gt; [B, num_heads, N, head_dim]</span></span>
<span id="cb5-29"></span>
<span id="cb5-30"></span>
<span id="cb5-31">        scores <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.matmul(query, key.transpose(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>))<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.head_dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span><span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">0.5</span>) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, num_heads, N, head_dim] * [B, num_heads, head_dim, N] -&gt; [B, num_heads, N, N] TC=O(B*N^2*d_k)</span></span>
<span id="cb5-32"></span>
<span id="cb5-33">        attn <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> F.softmax(scores, dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, num_heads, N, N]</span></span>
<span id="cb5-34"></span>
<span id="cb5-35">        final <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.matmul(attn, value).permute(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>).reshape(batch_size, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.d_k) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, num_heads, N, N] * [B, num_heads, N, head_dim] -&gt; [B, N, d_k]  TC=O(B*N^2*d_k)</span></span>
<span id="cb5-36">        projout <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.out(final) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k] -&gt; [B, N, d_model]</span></span>
<span id="cb5-37">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> projout <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_model]</span></span>
<span id="cb5-38"></span>
<span id="cb5-39"></span>
<span id="cb5-40">d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb5-41">d_k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb5-42"></span>
<span id="cb5-43">model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> MultiHeadVanillaAttention(d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model, num_heads<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, head_dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">32</span>).requires_grad_(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">eval</span>().to(device)</span>
<span id="cb5-44"></span>
<span id="cb5-45">n_tokens <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">16384</span></span>
<span id="cb5-46">inp <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, n_tokens, d_model, device<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>device)</span>
<span id="cb5-47"></span>
<span id="cb5-48">torch.cuda.synchronize()</span>
<span id="cb5-49">start <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> time.time()</span>
<span id="cb5-50">k<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">50</span></span>
<span id="cb5-51"><span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> _ <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(k):</span>
<span id="cb5-52">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">with</span> torch.no_grad():</span>
<span id="cb5-53">        out <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> model(inp)</span>
<span id="cb5-54">torch.cuda.synchronize()</span>
<span id="cb5-55"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">f"Time taken: </span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span>(time.time()<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>start)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>k<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">:.3f}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>)</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<pre><code>Time taken: 2.734</code></pre>
</div>
</div>
</section>
</section>
<section id="linear-attention" class="level2">
<h2 class="anchored" data-anchor-id="linear-attention">Linear Attention</h2>
<ul>
<li><p>Instead of using softmax, it tries to make it more general where this softmax function can be replaced by any other function</p></li>
<li><p>Kernel is some function which takes in two input vectors (query and key) and gives a single scalar output i.e.&nbsp;similarity score.</p></li>
<li><p>This softmax can also be replaced by some kernel which is some kind of similarity function (i.e.&nbsp;to have property of a similarity function).</p></li>
<li><p>Kernel can be decomposed into linear functions (feature functions)</p>
<ul>
<li><img src="https://latex.codecogs.com/png.latex?K(a,%20b)%20=%20%5Cphi(a)%5ET%5Cphi(b)"></li>
</ul></li>
<li><p>Feature function takes a vector as input and projects it into new feature space</p></li>
<li><p>The basic idea is instead of doing complicated non-linear function like softmax, can’t we just project a and b into higher dimensional space and just do the linear inner product</p></li>
<li><p>The attention mechanism is defined as <img src="https://latex.codecogs.com/png.latex?A_l(x)%20=%20V'%20=%20%5Ctext%7Bsoftmax%7D%20%5Cleft(%20%5Cfrac%7BQK%5ET%7D%7B%5Csqrt%7BD%7D%7D%20%5Cright)%20V">.</p></li>
<li><p>We can make the above equation more generalized by using a similarity function</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?V'_i%20=%20%5Cfrac%7B%5Csum_%7Bj=1%7D%5EN%20%5Ctext%7Bsim%7D(Q_i,%20K_j)%20V_j%7D%7B%5Csum_%7Bj=1%7D%5EN%20%5Ctext%7Bsim%7D(Q_i,%20K_j)%7D"></p></li>
<li><p>where we can think of <img src="https://latex.codecogs.com/png.latex?%5Ctext%7Bsim%7D(q,%20k)%20=%20%5Cexp%20%5Cleft(%20%5Cfrac%7Bq%5ET%20k%7D%7B%5Csqrt%7BD%7D%7D%20%5Cright)"></p></li>
<li><p>only constraint on sim is to give non-negative outputs</p></li>
<li><p>given a kernel with feature representation <img src="https://latex.codecogs.com/png.latex?%5Cvarphi(x)">, we can rewrite the above equation</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?V'_i%20=%20%5Cfrac%7B%5Csum_%7Bj=1%7D%5EN%20%5Cphi(Q_i)%5ET%20%5Cphi(K_j)%20V_j%7D%7B%5Csum_%7Bj=1%7D%5EN%20%5Cphi(Q_i)%5ET%20%5Cphi(K_j)%7D"></p></li>
<li><p>By making the use of associative property of matrix multiplication, we can take out Q from summation, because it is independent of j</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?V'_i%20=%20%5Cfrac%7B%5Cphi(Q_i)%5ET%20%5Csum_%7Bj=1%7D%5EN%20%5Cphi(K_j)%20V_j%5ET%7D%7B%5Cphi(Q_i)%5ET%20%5Csum_%7Bj=1%7D%5EN%20%5Cphi(K_j)%7D"> (4)</p></li>
<li><p>And finally we can convert it into vectorized format</p></li>
<li><p><img src="https://latex.codecogs.com/png.latex?%5Cleft(%20%5Cphi(Q)%20%5Cphi(K)%5ET%20%5Cright)%20V%20=%20%5Cphi(Q)%20%5Cleft(%20%5Cphi(K)%5ET%20V%20%5Cright)"></p></li>
<li><p>It is linear because we can compute numerator and denominator and use it for all the queries [The eqn before vectorized one]</p></li>
<li><p>For softmax attention, complexity is O(N^2 * max(D, M)), where D is dimensionality for query and key, M is for value</p></li>
<li><p>For linear attention, complexity is O(NCM), where C is feature map projection dim and M is for value</p></li>
<li><p>Linearization of exact softmax attention is not feasible because of the exponential kernel, which is of infinite dimension and can’t be stored on a computer (expansion of e^x is infinitely many terms)</p></li>
<li><p>That’s why it is better to use some kind of polynomial feature representation</p></li>
<li><p>The author chose elu instead of relu to avoid setting gradients to 0 when input was negative</p></li>
</ul>
<div class="callout callout-style-default callout-tip callout-titled">
<div class="callout-header d-flex align-content-center">
<div class="callout-icon-container">
<i class="callout-icon"></i>
</div>
<div class="callout-title-container flex-fill">
Tip
</div>
</div>
<div class="callout-body-container callout-body">
<p>The key trick in linear attention is to avoid explicitly creating <img src="https://latex.codecogs.com/png.latex?%5Cphi(Q)%5Cphi(K)%5ET"> first. By computing <img src="https://latex.codecogs.com/png.latex?%5Cphi(K)%5ET%20V"> before multiplying with <img src="https://latex.codecogs.com/png.latex?%5Cphi(Q)">, the attention can be computed more efficiently for long sequences.</p>
</div>
</div>
<section id="single-head-linear-attention-pytorch-code" class="level3">
<h3 class="anchored" data-anchor-id="single-head-linear-attention-pytorch-code">Single Head Linear Attention PyTorch Code</h3>
<div id="3b9ee8ef" class="cell" data-execution_count="4">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb7" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb7-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb7-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb7-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb7-4"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> time</span>
<span id="cb7-5"></span>
<span id="cb7-6">device <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.device(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"cuda"</span> <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> torch.cuda.is_available() <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span> <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"cpu"</span>)</span>
<span id="cb7-7"></span>
<span id="cb7-8"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> SingleHeadLinearAttention(nn.Module):</span>
<span id="cb7-9">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, in_features, out_features):</span>
<span id="cb7-10">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb7-11">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> in_features</span>
<span id="cb7-12">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> out_features</span>
<span id="cb7-13">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wq <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.in_features, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.out_features)</span>
<span id="cb7-14">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wk <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.in_features, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.out_features)</span>
<span id="cb7-15">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wv <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.in_features, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.out_features)</span>
<span id="cb7-16"></span>
<span id="cb7-17">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> forward(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, x):</span>
<span id="cb7-18">        query <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wq(x) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb7-19">        key <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wk(x)   <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">#[B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb7-20">        value <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.Wv(x) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_model] * [d_model, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_model*d_k)</span></span>
<span id="cb7-21"></span>
<span id="cb7-22">        query <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> F.elu(query) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k]</span></span>
<span id="cb7-23">        key <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> F.elu(key) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span> <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k]</span></span>
<span id="cb7-24"></span>
<span id="cb7-25">        scores <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.matmul(key.transpose(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>), value) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, d_k, N] * [B, N, d_k] -&gt; [B, d_k, d_k] TC=O(B*N*d_k^2)</span></span>
<span id="cb7-26"></span>
<span id="cb7-27">        final <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.matmul(query, scores) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k] * [B, d_k, d_k] -&gt; [B, N, d_k] TC=O(B*N*d_k^2)</span></span>
<span id="cb7-28">        k_sum <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">sum</span>(key, dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>).unsqueeze(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb7-29"></span>
<span id="cb7-30">        normalizer <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.matmul(query, k_sum) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N , d_k] * [B, d_k, 1] -&gt; [B, N, 1] TC=O(B*N*d_k)</span></span>
<span id="cb7-31">        eps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">1e-6</span> <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># To use in case we don't divide by 0</span></span>
<span id="cb7-32"></span>
<span id="cb7-33">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> final<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>(normalizer <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> eps) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [B, N, d_k]</span></span>
<span id="cb7-34"></span>
<span id="cb7-35">d_model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb7-36">d_k <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">512</span></span>
<span id="cb7-37"></span>
<span id="cb7-38">model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> SingleHeadLinearAttention(in_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_model, out_features <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> d_k).requires_grad_(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">eval</span>().to(device)</span>
<span id="cb7-39"></span>
<span id="cb7-40">n_tokens <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">16384</span></span>
<span id="cb7-41">inp <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, n_tokens, d_model, device<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>device)</span>
<span id="cb7-42"></span>
<span id="cb7-43">torch.cuda.synchronize()</span>
<span id="cb7-44">start <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> time.time()</span>
<span id="cb7-45">k<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">50</span></span>
<span id="cb7-46"><span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> _ <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(k):</span>
<span id="cb7-47">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">with</span> torch.no_grad():</span>
<span id="cb7-48">        out <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> model(inp)</span>
<span id="cb7-49">torch.cuda.synchronize()</span>
<span id="cb7-50"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">f"Time taken: </span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span>(time.time()<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span>start)<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>k<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">:.3f}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>)</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<pre><code>Time taken: 0.057</code></pre>
</div>
</div>
<table class="caption-top table">
<colgroup>
<col style="width: 33%">
<col style="width: 33%">
<col style="width: 33%">
</colgroup>
<thead>
<tr class="header">
<th>Method</th>
<th>Main idea</th>
<th>Complexity bottleneck</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td>Single Head Vanilla Attention</td>
<td>One set of query, key, and value projections</td>
<td>Forms an <img src="https://latex.codecogs.com/png.latex?N%20%5Ctimes%20N"> attention matrix</td>
</tr>
<tr class="even">
<td>Multi Head Vanilla Attention For loop</td>
<td>Computes each head separately and concatenates outputs</td>
<td>Still forms one <img src="https://latex.codecogs.com/png.latex?N%20%5Ctimes%20N"> matrix per head</td>
</tr>
<tr class="odd">
<td>Multi Head Vanilla Attention</td>
<td>Vectorizes the heads into one batched operation</td>
<td>Same quadratic attention cost, but better parallelism</td>
</tr>
<tr class="even">
<td>Single Head Linear Attention</td>
<td>Uses a feature map and associativity to avoid explicit softmax attention</td>
<td>Depends on feature dimension instead of storing full <img src="https://latex.codecogs.com/png.latex?N%20%5Ctimes%20N"> attention</td>
</tr>
</tbody>
</table>


</section>
</section>

 ]]></description>
  <category>Deep Learning</category>
  <guid>https://riteshrm.github.io/posts/attention-mechanism/</guid>
  <pubDate>Mon, 12 Jan 2026 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/attention-mechanism/attn_resized_thumbnail.png" medium="image" type="image/png" height="82" width="144"/>
</item>
<item>
  <title>Hands on LLMs: Chapter-Wise Summary</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/hands-on-llms/</link>
  <description><![CDATA[ 





<ul>
<li>This is completely based on <a href="https://www.oreilly.com/library/view/hands-on-large-language/9781098150952/">Hands on LLMs</a></li>
</ul>
<section id="chapter-1introduction-to-llms" class="level1">
<h1>Chapter-1[Introduction to LLMs]</h1>
<ul>
<li><p>Bag of Words:- We have a predefined vocabulary, which is used to creat a vector, where each vector index contains the count of that particular word index in vocab</p></li>
<li><p>word2vec:- It is trained by using a pair(whether dfferent or same semantic meaning) of words</p></li>
<li><p>Bag of words create embedding at documet level, whereas word2vec generates embedding for words only</p></li>
<li><p>Representation Models are encoder only models</p></li>
<li><p>Generative Models are decoder only models</p></li>
<li><p>BERT(Bidirectional Encoder Represenations from Transformers)</p>
<ul>
<li>It is trained by a tecique called masked language modeling, where this method masks a part of the input for the model to predict</li>
<li>Pretrain on large dataset using masked language modng and then fine tune it for down stream tasks</li>
</ul></li>
<li><p>Creating an LLM consists of typically at least two steps:</p>
<ul>
<li>Language Modeling(Pretraining):- An LLM is trained on a vast corpus of internet text allowing the model to learn grammar, context and language patterns.</li>
<li>Fine Tuning(Post Training):- Further training the previously trained model on narrower tasks.</li>
</ul></li>
</ul>
</section>
<section id="chapter-2tokens-and-embeddings" class="level1">
<h1>Chapter-2[Tokens and Embeddings]</h1>
<ul>
<li><p>Partial tokens (like “izing”, and “ic”) have a special hidden character at their beginning that indicates that they are connected with the token that precedes them in the text.</p></li>
<li><p>Word Tokens</p></li>
<li><p>Subword Tokens</p></li>
<li><p>Character Tokens</p></li>
<li><p>Byte Tokens</p></li>
<li><p>Designing Large Language Model Applications. (For tokenizers)</p></li>
<li><p>BERT tokenizers are based on wordpiece, introduced in Japanese and Korean voice search [https://ieeexplore.ieee.org/document/6289079]</p></li>
<li><p>GPT-2 is based on Byte Pair Encoding (BPE), introduced in Neural machine translation of rare words with subword units [https://arxiv.org/abs/1508.07909]</p></li>
<li><p>Flan-T5 is based on SentencePiece, introduced in “SentencePiece: simple and language independent subword tokenizer and detokenizer for neural text processing”, which supports BPE and unigram language model</p></li>
<li><p>There are three major factors that dictate how a tokenizer breaks down an input prompt</p>
<ul>
<li>Tokenization method (BPE, WordPiece, etc.)
<ul>
<li>Each of these methods outlines an algorithm for how to choose an appropriate set of tokens to represent a dataset</li>
</ul></li>
<li>Tokenizer Design choices (vocab size, special tokens)
<ul>
<li>vocab size:- How many tokens to keep in tokenizers vocabulary</li>
<li>special tokens:- What special tokens do we want the model to keep track of. We can add as many of these as we want</li>
</ul></li>
<li>Capitalization:- Whether to convert caps to lower or not</li>
</ul></li>
<li><p>More details on training tokenizer at:-</p>
<ul>
<li>Tokenizers section of the Hugging Face course [https://huggingface.co/learn/nlp-course/chapter6/1?fw=pt]</li>
<li>Natural Language Processing with Transformers, Revised Edition [https://www.oreilly.com/library/view/natural-language-processing/9781098136789/]</li>
</ul></li>
</ul>
</section>
<section id="chapter-3looking-inside-large-language-models" class="level1">
<h1>Chapter-3[Looking Inside Large Language Models]</h1>
<ul>
<li><p>Autoregressive Models: The models that consume their earlier predictions to make later predictions</p></li>
<li><p>Three Major components of LLMs are:</p>
<ul>
<li>Tokenizer</li>
<li>Stack of Transformer Blocks</li>
<li>A language modeling head</li>
</ul></li>
<li><p>Context length (Number of streams):- Number of previous tokens which will be considered for the prediction of current token</p></li>
<li><p>KVCache:- Keeping the previously calculated key and value so that we dont have to recalculate the same again and again</p></li>
<li><p>Components of Transformer Blocks</p>
<ul>
<li>Attention Layer:- Incorporates contextual information to allow the model to better capture the nuance of language.</li>
<li>FeedForward Layer:- It is able to store information and make predictions and interpolations from data it was trained on.</li>
</ul></li>
<li><p>Two main steps are involved in the attention mechanism:</p>
<ul>
<li>Relevance scoring: How much previous tokens are relevant to the curren token being processed.</li>
<li>Combining Information:- Using scores, combine the information from the various positions into a single output vector</li>
</ul></li>
<li><p>More efficient Attention</p>
<ul>
<li>Local/Sparse Attention:- Sparse Attention limits the context of previous tokens that the model can attend to.</li>
<li>Multi-query:- Unique Queries but same key and value for all the head</li>
<li>Grouped-query:- Dividing queries in groups and then key, value will be same for the queries within a group</li>
<li>RoPE:- Added to queries and keys before calculating the score in Attention blocks</li>
</ul></li>
</ul>
</section>
<section id="chapter-4text-classification" class="level1">
<h1>Chapter-4[Text Classification]</h1>
<ul>
<li><p>In case of no lableld data, we can define our desired labels and then encode both labels and given text and then use cosine_similarity</p></li>
<li><p>Directly using pretrained models for sentiment classification</p></li>
<li><p>Using a simple classifier on top of embedding generator</p></li>
<li><p>If we don’t have labeled data then we can use cosine similarity to find out the label</p></li>
<li><p>We can use generative models also</p></li>
</ul>
</section>
<section id="chapter-5text-clustering-and-topic-modeling" class="level1">
<h1>Chapter-5[Text Clustering and Topic Modeling]</h1>
<ul>
<li><p>A common Pipeline for Text Clustering</p>
<ul>
<li>Convert the input documents to embeddings with an embedding model</li>
<li>Reduce the dimensionality of embeddings with a dimensionality reduction model (UMAP as it tends to handle nonlinear relationships and structures a bit better than PCA)</li>
<li>Find groups of semantically similar documents with a cluster model (using HDBSCAN)</li>
</ul></li>
<li><p>c-TF-IDF</p>
<ul>
<li>TF:- Frequency of word X in class C</li>
<li>IDF:- log(average number of words per class/frequency of X across all classes)</li>
</ul></li>
<li><p>BERTopic [https://maartengr.github.io/BERTopic/getting_started/best_practices/best_practices.html]</p></li>
<li><p>After getting the keywords using c-TF-IDF, we can use MMR(maximal marginal relevance) to keep only the diverse keywords, we can also use KeyBERTInspired to fine-tune the topic representations</p></li>
<li><p>Additonally, we can use LLMs to further improve interpretability of topics</p></li>
</ul>
</section>
<section id="chapter-6prompt-engineering" class="level1">
<h1>Chapter-6[Prompt Engineering]</h1>
<ul>
<li><p>Temperature:- It controls the randomness or creativity of the text generated. It defines how likely it is to choose tokens that are less probable. A temperature of 0 generates the same response every time because it always choose the most likely word. A higher value allows less probable words to be generated</p></li>
<li><p>Divide all the logits before passing to softmax</p></li>
<li><p>top_p:- It is also known as nucleus sampling, is a sampling technique that controls which subset of tokens (the nucleus) the LLM can consider. It will consider tokens until it reaches their cumulative probability. If we set top_p to 0.1, it will consider tokens until it reache that value.</p></li>
<li><p>top_k:- same as top_p, LLM will only consider the top 100 most probable tokens if you set its value to 100.</p></li>
<li><p>Table 6.1 from page 172</p></li>
<li><p>Self-consistency:- Sampling from multiple paths for the same prompt and using the voting technique for the best one</p></li>
<li><p>CoT:- Solving the complex problems step by step</p></li>
<li><p>ToT:- Generates different solutions and then selects the best one and continues. This method requires so many calls to the model. But we can change it using a prompt, we can ask the model to mimic the behavior</p></li>
</ul>
</section>
<section id="chapter-7advanced-text-generation-techniques-and-tools" class="level1">
<h1>Chapter-7[Advanced Text Generation Techniques and Tools]</h1>
<ul>
<li>PromptTemplate from langchain</li>
<li>Can use LLMChain to create a chain</li>
<li>Can use ConversationBufferMemory to have access to chat history</li>
<li>Can use ConversationBufferWindowMemory to keep only last k chats–&gt; Can use ConversationSummaryMemory alongside an LLM to store the summary fo conversation instead of storing raw chats</li>
<li>ReAct:- Reasoning and Acting
<ul>
<li>Thought:- thought about the input prompt</li>
<li>Action:- based on thought action is triggered, it is generally an external tool like calculator or search engine</li>
<li>Observation:- finally the results of action are returned to the LLM it observes the output</li>
</ul></li>
</ul>
</section>
<section id="chapter-8semantic-search-and-retrieval-augmented-generation" class="level1">
<h1>Chapter-8[Semantic Search and Retrieval-Augmented Generation]</h1>


</section>

 ]]></description>
  <category>Books</category>
  <guid>https://riteshrm.github.io/posts/hands-on-llms/</guid>
  <pubDate>Mon, 27 Jan 2025 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/hands-on-llms/traing_work_flow_of_llm.png" medium="image" type="image/png" height="75" width="144"/>
</item>
<item>
  <title>Meta Learning: Chapter-Wise Summary</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/meta-learning/</link>
  <description><![CDATA[ 





<section id="from-not-being-able-to-program-to-deep-learning-expert" class="level1">
<h1>From not being able to program to deep learning expert</h1>
<ul>
<li>Understand the value of Stack Overflow, documentation and how to reach both.</li>
<li>Learn to use a code editor really well.</li>
<li>Learn to use git for version control.</li>
<li>Learn how to use local or cloud VM.</li>
<li>How to complete a lecture:-
<ul>
<li>Watch the lecture</li>
<li>Open the notebook and try to find out how all the pieces fit together.</li>
<li>If you encounter some new functions then it will be good to know about them.</li>
<li>Tweak the hyperparameters and see how it performs.</li>
<li>Once you understand, try to create a new notebook recreating the training pipeline that is demonstrated in lecture.</li>
<li>Now if everything is working well, then you might want to test the same technique on another dataset of similar type.</li>
</ul></li>
</ul>
</section>
<section id="theory-vs-practice-" class="level1">
<h1>Theory vs practice:-</h1>
<ul>
<li>If you aim to reach the highest echelons of deep learning research, you first and foremost need to be a great practitioner!</li>
<li>For best effects, use one cup of theory, one cup of practice. Rinse and repeat</li>
<li>We are reading papers, but without training actual models, without the experience of applying what we are learning to real-life problem, we are missing a very important feedback loop.</li>
</ul>
</section>
<section id="programming-is-about-what-you-have-to-say-" class="level1">
<h1>Programming is about what you have to say:-</h1>
<ul>
<li>Your ability as a developer is measured by the utility of the things you can express in a language.</li>
<li>Reading and writing a lot of code is the best way to learn a programming language.</li>
</ul>
</section>
<section id="the-secret-of-good-developers-" class="level1">
<h1>The secret of good developers:-</h1>
<ul>
<li>Go for long, uninterrupted sessions to avoid context switching.</li>
</ul>
</section>
<section id="the-best-way-to-improve-as-a-developer-" class="level1">
<h1>The best way to improve as a developer:-</h1>
<ul>
<li>You don’t sharpen your skills with resources, books, or articles. You sharpen your skills with practice. If you want to get better, go do the thing.</li>
<li>Read and write a lot of code.</li>
</ul>
</section>
<section id="how-to-use-your-tools-to-achieve-a-state-of-flow" class="level1">
<h1>How to use your tools to achieve a state of flow</h1>
<ul>
<li>You are in a state of flow when nothing separates you and your work</li>
<li>That’s why many programmers spend a lot of time studying their editors</li>
<li>We are always somewhere between two extremes (state of flow)</li>
<li>All we can do is take small steps and see if it is taking us towards the ideal.</li>
<li>This can take our productivity to a whole new level.</li>
</ul>
</section>
<section id="use-reality-as-your-mirror-" class="level1">
<h1>Use reality as your mirror:-</h1>
<ul>
<li>If you want to live a different life tomorrow than you are living today, you have to put your beliefs to the test.</li>
<li>The stronger the emotions involved in a situation, the higher the chance you are not seeing things clearly.</li>
<li>Suppose you want to post something and you are afraid that people whom I respect will unfollow me or they will say I am stupid, but that doesn’t matter in the long run.</li>
<li>Post it and you will learn on the way.</li>
<li>Thinking about writing something isn’t doing the thing.</li>
</ul>
</section>
<section id="do-genuine-work-it-compounds-" class="level1">
<h1>Do genuine work (it compounds):-</h1>
<ul>
<li>Reading a book without taking notes is like discovering a new territory and forgetting to draw a map.</li>
<li>Genuine work moves the atoms in the universe.</li>
<li>Always make notes.</li>
<li>Share whatever you have made.</li>
<li>The more atoms you move the better the feedback you receive and the greater the extent to which you can reflect on what you are learning.</li>
</ul>
</section>
<section id="the-hidden-game-of-machine-learning-" class="level1">
<h1>The hidden game of machine learning:-</h1>
<ul>
<li>At the core of machine learning lies the ability to generalize to unseen data.</li>
<li><a href="https://www.fast.ai/posts/2017-11-13-validation-sets.html">How (and why) to create a good validation set blog post by Rachel Thomas</a></li>
<li><a href="https://work.caltech.edu/telecourse.html">Learning From Data: A short course by Yaser S. Abu-Mostafa</a></li>
<li><a href="https://millengustavo.github.io/build-ml-app/">Building Machine Learning Powered Applications: Going from Idea to Product by Emmanuel Ameisen</a></li>
</ul>
</section>
<section id="how-to-structure-a-machine-learning-project-" class="level1">
<h1>How to structure a machine learning project:-</h1>
<ul>
<li><p>The main condition for a healthy machine learning project is a good train-val-test split.</p></li>
<li><p>Always have a baseline to get to know whether i am going in right direction or not or what can be done next.</p></li>
<li><p>Don’t run experiments just for the sake of tweaking hyperparameters, instead invest time in exploring other architectures, developing diagnostic code.</p></li>
<li><p>The idea is to always move in small increments, using simpler models as a stepping stone to more complex ones.</p></li>
<li><p>Define loss and implement it on simple model consisting of few layers and then check by passing a batch if output is not all zeros and the output shape is required shape.</p></li>
<li><p>Create a subset of train data(1%) to check whether the modified code is working and the we are going in the right direction.</p></li>
<li><p>Read as much as possible related to the domain you are working on so that our mind can work on the solution and analyze what to do next.</p></li>
<li><p>Go slowly and give attention to each component of the pipeline and grow them systematically.</p></li>
</ul>
</section>
<section id="how-to-win-at-kaggle-" class="level1">
<h1>How to win at Kaggle:-</h1>
<ul>
<li><p>Join the competition early.</p></li>
<li><p>Learn about the problem domain and data</p></li>
<li><p>Write diagnostic code and identify where model is struggling.</p></li>
<li><p>Follow Kaggle forums and read daily.</p></li>
<li><p>Try to find out the relevant research papers and see if it is useful in solving the problem.</p></li>
<li><p>You can read blogs related to the problem you are solving.</p></li>
<li><p>While early in the competition, try on different architectures instead of tweaking the hyperparameters.</p></li>
<li><p>How do we know that we are moving in the right direction? So first of all create a baseline and make a submission. The submission can consist of all zeros.</p></li>
<li><p>Try to find out a validation split that will track the public leaderboard.</p></li>
<li><p>A proper validation split lies at the heart of any good Kaggle submission.</p></li>
<li><p>To know that if we are going in the right direction, see if the local results matches with the leaderboard. If so then you are going in the right direction and if not then try to find out other ways of splitting the data or something else.</p></li>
<li><p>You can do ensembling also. the idea is to cancel out the errors from individual model in a hope that their errors are not correlated.</p></li>
<li><p>A related technique is training with cross-validation, where you train multiple models withholding different parts of the data for validation and then combine the results from them.</p></li>
</ul>
</section>
<section id="the-best-hardware-for-deep-learning-" class="level1">
<h1>The best hardware for deep learning:-</h1>
<ul>
<li><a href="https://timdettmers.com/2023/01/30/which-gpu-for-deep-learning/#more-6">Follow this blog to know more about GPUs</a></li>
</ul>
</section>
<section id="debugging-with-ease-is-a-superpower-" class="level1">
<h1>Debugging with ease is a superpower:-</h1>
<ul>
<li><a href="https://x.com/radekosmulski/status/945739571735748609">Radek Osmulski’s Favorite recent Jupyter notebook discovery - the %debug magic:</a></li>
</ul>
</section>
<section id="time-yourself-" class="level1">
<h1>Time yourself:-</h1>
<ul>
<li>Always keep track of the time which you devote to various activities.</li>
<li>%%timeit</li>
</ul>
</section>
<section id="you-cant-learn-a-profession-by-studying-a-textbook-" class="level1">
<h1>You can’t learn a profession by studying a textbook:-</h1>
<ul>
<li>Extensive practice is very important alongside theory.</li>
</ul>
</section>
<section id="on-finding-a-job-" class="level1">
<h1>On finding a job:-</h1>
<ul>
<li>The best approach is to showcase your work, by helping others.</li>
<li>Reach out to the people who know you and can help you.</li>
</ul>
</section>
<section id="the-deep-learning-party-is-on-twitter-" class="level1">
<h1>The deep learning party is on Twitter:-</h1>
<ul>
<li>you will find all the amazing people there</li>
</ul>
</section>
<section id="share-your-work-" class="level1">
<h1>Share your work:-</h1>
<ul>
<li><a href="https://www.fast.ai/posts/2017-12-18-personal-brand.html">Making Peace with Personal Branding</a></li>
</ul>
</section>
<section id="when-to-start-sharing-your-work-" class="level1">
<h1>When to start sharing your work:-</h1>
<ul>
<li>The sooner, the better!</li>
<li>With every piece that we produce, we hone our communication skills</li>
</ul>
</section>
<section id="i-am-scared-to-share-my-work-help" class="level1">
<h1>I am scared to share my work! Help!</h1>
<ul>
<li>Where some see failure, others see cheap feedback.</li>
<li>If you don’t like something then you can always delete it.</li>
</ul>
</section>
<section id="what-to-focus-on-in-sharing-your-work-" class="level1">
<h1>What to focus on in sharing your work:-</h1>
<ul>
<li>Speak to your experience.</li>
<li>You don’t have to share something outside of your experience.</li>
</ul>
</section>
<section id="dont-lose-sight-of-what-is-important-" class="level1">
<h1>Don’t lose sight of what is important:-</h1>
<ul>
<li>You won a Kaggle competition that’s good but never ever forget why you have started.</li>
<li>You don’t need followers or likes or even social media to learn.</li>
<li>Nearly all of the best DL engineers I(Radek Osmulski) know are either very quiet or completely silent on Twitter</li>
</ul>
</section>
<section id="make-mental-space-for-what-matters-" class="level1">
<h1>Make mental space for what matters:-</h1>
<ul>
<li>Peace of mind is the most important prerequisite for creative work.</li>
<li>Avoid using social media too much!</li>
</ul>
</section>
<section id="to-engage-afterburners-find-a-mentor-" class="level1">
<h1>To engage afterburners, find a mentor:-</h1>
<ul>
<li>Find a mentor, who is good at something you care about.</li>
<li>The mentor doesn’t need to know you.</li>
<li>In general, we want to get answers from the people who are like us and have gone through that path and the people who are not like us to get to know about more ideas.</li>
<li>Always make your message as concise and clear as you can.</li>
</ul>
</section>
<section id="the-biggest-regret-of-fast.ai-students-" class="level1">
<h1>The biggest regret of fast.ai students:-</h1>
<ul>
<li>I wished I spent more time coding and experimenting and less time studying in a more traditional sense.</li>
<li>100% learning -&gt; x% doing/100-x% real learning.</li>
<li>Shortest path to understand how something works leads through practice.</li>
<li>80% doing and 20% reading theory.</li>
</ul>
</section>
<section id="persistence-is-everything-" class="level1">
<h1>Persistence is everything:-</h1>
<ul>
<li>At any given moment, as you put in the work, you can barely notice a difference in your life. But the longer you stay the course the more rewarding the journey becomes.</li>
<li>Learning compounds and you need to give it time before you start seeing the exponential results.</li>
<li>Combine persistence with community involvement and you cannot be stopped.</li>
</ul>
</section>
<section id="change-is-about-what-not-to-do-" class="level1">
<h1>Change is about what not to do:-</h1>
<ul>
<li>Ceasing how we have done things up to now is harder than taking on new approach.</li>
<li>Try to find out the behaviors which are no longer helpful to pursuing your goals and replace them with some meaningful.</li>
</ul>
</section>
<section id="learning-might-just-be-enough" class="level1">
<h1>Learning might just be enough</h1>
<ul>
<li>A good strategy towards learning is to observe whether you are getting the results that you are after and if you are not then change your approach.</li>
</ul>
</section>
<section id="more-perspectives-on-mentoring-" class="level1">
<h1>More perspectives on mentoring:-</h1>
<ul>
<li>If you want to catch the attention of someone you admire give yourself a job working for them.</li>
<li>Learn in public.
<ul>
<li>Write blogs and tutorials and cheatsheets.</li>
<li>Speak at meetups and conferences.</li>
<li>Ask and answer things on Stack Overflow or Reddit. Avoid the walled gardens like Slack and Discord, they’re not public.</li>
<li>Make YouTube videos or Twitch streams.</li>
<li>Start a newsletter.</li>
<li>Draw cartoons</li>
</ul></li>
<li>Make the thing you wish you had found when you were learning.</li>
<li>Don’t judge results by claps or tweets or stars or upvotes, just talk to yourself from 3 months ago.</li>
<li>by far the biggest beneficiary of you trying to help past you is future you. If others benefit, that’s icing.</li>
<li>Don’t stop there:
<ul>
<li>Enjoyed a coding video? Reach out to the speaker/instructor and thank them, and ask questions.</li>
<li>Make PR’s to libraries you use.</li>
<li>Make your own libraries no one will ever use.</li>
<li>Clone stuff you like, from scratch, to see how they work.</li>
<li>Teach workshops.</li>
<li>Go to conferences and summarize what you learned.</li>
</ul></li>
<li>Try your best to be right, but don’t worry when you’re wrong, and let the internet correct you when you are inevitably wrong.</li>
<li>Talk while you code.</li>
<li>Whenever someone wants some help, then you should be always ready to help them because these are some of the most in-demand people in tech.</li>
</ul>
</section>
<section id="tap-into-the-power-of-the-community-to-learn-faster" class="level1">
<h1>Tap into the power of the community to learn faster</h1>
<ul>
<li>Instead of asking questions only try to answer more.</li>
<li>Joining community will help you in better communication, learn from other’s.</li>
</ul>
</section>
<section id="energize" class="level1">
<h1>Energize</h1>
<ul>
<li>Yoga can help.</li>
<li>Time-restricted eating and its primary benefit is restore hormonal balance.</li>
</ul>


</section>

 ]]></description>
  <category>Books</category>
  <guid>https://riteshrm.github.io/posts/meta-learning/</guid>
  <pubDate>Sat, 06 Jul 2024 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/meta-learning/metalearning_resized_thumbnail.png" medium="image" type="image/png" height="82" width="144"/>
</item>
<item>
  <title>Quantization in Depth</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/quantization-in-depth/</link>
  <description><![CDATA[ 





<ul>
<li><p>This is completely based on <a href="https://learn.deeplearning.ai/courses/quantization-in-depth/lesson/1/introduction">Quantization in Depth</a></p></li>
<li><p>For the code part, you can checkout this <a href="https://github.com/riteshrm/Quantization-in-Depth-deeplearning.ai-">link</a></p></li>
</ul>
<section id="quantize-and-de-quantize-a-tensor" class="level3">
<h3 class="anchored" data-anchor-id="quantize-and-de-quantize-a-tensor">Quantize and De-quantize a tensor</h3>
<ul>
<li>Advantages of Quantization
<ul>
<li>Smaller model</li>
<li>Speed gains
<ul>
<li>Memory bandwidth</li>
<li>Faster operations
<ul>
<li>GEMM: General Matrix Multiply(matrix to matrix multiplication)</li>
<li>GEMV: General Matrix Vector Multiplication (matrix to vector multiplication)</li>
</ul></li>
</ul></li>
</ul></li>
<li>Challenges of Quantization
<ul>
<li>Quantization error</li>
<li>Retraining (Quantization Aware Training)</li>
<li>Limited Hardware support</li>
<li>Calibration dataset needed</li>
<li>packing/unpacking</li>
</ul></li>
<li>getting q:-
<ul>
<li>r = s(q-z) q = int(round(r/s+z))</li>
</ul></li>
</ul>
<div id="34931bb4" class="cell" data-execution_count="1">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb1" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb1-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb1-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> seaborn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> sns</span>
<span id="cb1-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> matplotlib.pyplot <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> plt</span>
<span id="cb1-4"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">from</span> matplotlib.colors <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> ListedColormap</span>
<span id="cb1-5"></span>
<span id="cb1-6"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">#Helper functions to visualize</span></span>
<span id="cb1-7"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> plot_matrix(tensor, ax, title, vmin<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>, vmax<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, cmap<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>):</span>
<span id="cb1-8">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">"""</span></span>
<span id="cb1-9"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">    Plot a heatmap of tensors using seaborn</span></span>
<span id="cb1-10"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">    """</span></span>
<span id="cb1-11">    sns.heatmap(tensor.cpu().numpy(), ax<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>ax, vmin<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>vmin, vmax<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>vmax, cmap<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>cmap, annot<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span>, fmt<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">".2f"</span>, cbar<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>)</span>
<span id="cb1-12">    ax.set_title(title)</span>
<span id="cb1-13">    ax.set_yticklabels([])</span>
<span id="cb1-14">    ax.set_xticklabels([])</span>
<span id="cb1-15"></span>
<span id="cb1-16"></span>
<span id="cb1-17"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> plot_quantization_errors(original_tensor, quantized_tensor, dequantized_tensor, dtype <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.int8, n_bits <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">8</span>):</span>
<span id="cb1-18">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">"""</span></span>
<span id="cb1-19"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">    A method that plots 4 matrices, the original tensor, the quantized tensor</span></span>
<span id="cb1-20"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">    the de-quantized tensor and the error tensor.</span></span>
<span id="cb1-21"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">    """</span></span>
<span id="cb1-22">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Get a figure of 4 plots</span></span>
<span id="cb1-23">    fig, axes <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> plt.subplots(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">4</span>, figsize<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">15</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">4</span>))</span>
<span id="cb1-24"></span>
<span id="cb1-25">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Plot the first matrix</span></span>
<span id="cb1-26">    plot_matrix(original_tensor, axes[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>], <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'Original Tensor'</span>, cmap<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>ListedColormap([<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'white'</span>]))</span>
<span id="cb1-27"></span>
<span id="cb1-28">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Get the quantization range and plot the quantized tensor</span></span>
<span id="cb1-29">    q_min, q_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.iinfo(dtype).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">min</span>, torch.iinfo(dtype).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">max</span></span>
<span id="cb1-30">    plot_matrix(quantized_tensor, axes[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>], <span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">f'</span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span>n_bits<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">-bit Linear Quantized Tensor'</span>, vmin<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>q_min, vmax<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>q_max, cmap<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'coolwarm'</span>)</span>
<span id="cb1-31"></span>
<span id="cb1-32">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Plot the de-quantized tensors</span></span>
<span id="cb1-33">    plot_matrix(dequantized_tensor, axes[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>], <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'Dequantized Tensor'</span>, cmap<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'coolwarm'</span>)</span>
<span id="cb1-34"></span>
<span id="cb1-35">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Get the quantization errors</span></span>
<span id="cb1-36">    q_error_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">abs</span>(original_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> dequantized_tensor)</span>
<span id="cb1-37">    plot_matrix(q_error_tensor, axes[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>], <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'Quantization Error Tensor'</span>, cmap<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>ListedColormap([<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'white'</span>]))</span>
<span id="cb1-38"></span>
<span id="cb1-39">    fig.tight_layout()</span>
<span id="cb1-40">    plt.show()</span>
<span id="cb1-41"></span>
<span id="cb1-42"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> linear_q_with_scale_and_zero_point(</span>
<span id="cb1-43">    tensor, scale, zero_point, dtype <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.int8):</span>
<span id="cb1-44"></span>
<span id="cb1-45">    scaled_and_shifted_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span> scale <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> zero_point</span>
<span id="cb1-46"></span>
<span id="cb1-47">    rounded_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">round</span>(scaled_and_shifted_tensor)</span>
<span id="cb1-48"></span>
<span id="cb1-49">    q_min <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.iinfo(dtype).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">min</span></span>
<span id="cb1-50">    q_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.iinfo(dtype).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">max</span></span>
<span id="cb1-51"></span>
<span id="cb1-52">    q_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> rounded_tensor.clamp(q_min,q_max).to(dtype)</span>
<span id="cb1-53">    </span>
<span id="cb1-54">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> q_tensor</span>
<span id="cb1-55"></span>
<span id="cb1-56">test_tensor<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.tensor(</span>
<span id="cb1-57">    [[<span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">191.6</span>, <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">13.5</span>, <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">728.6</span>],</span>
<span id="cb1-58">     [<span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">92.14</span>, <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">295.5</span>,  <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">184</span>],</span>
<span id="cb1-59">     [<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>,     <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">684.6</span>, <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">245.5</span>]])</span>
<span id="cb1-60"></span>
<span id="cb1-61">scale <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="fl" style="color: #AD0000;
background-color: null;
font-style: inherit;">3.5</span></span>
<span id="cb1-62">zero_point <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">70</span></span>
<span id="cb1-63"></span>
<span id="cb1-64">quantized_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> linear_q_with_scale_and_zero_point(</span>
<span id="cb1-65">    test_tensor, scale, zero_point)</span>
<span id="cb1-66"></span>
<span id="cb1-67"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> linear_dequantization(quantized_tensor, scale, zero_point):</span>
<span id="cb1-68">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> scale <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> (quantized_tensor.<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">float</span>() <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> zero_point)</span>
<span id="cb1-69"></span>
<span id="cb1-70">dequantized_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> linear_dequantization(</span>
<span id="cb1-71">    quantized_tensor, scale, zero_point)</span>
<span id="cb1-72"></span>
<span id="cb1-73">plot_quantization_errors(test_tensor, quantized_tensor,</span>
<span id="cb1-74">                         dequantized_tensor)</span></code></pre></div></div>
<div class="cell-output cell-output-display">
<div>
<figure class="figure">
<p><img src="https://riteshrm.github.io/posts/quantization-in-depth/index_files/figure-html/cell-2-output-1.png" width="1430" height="374" class="figure-img"></p>
</figure>
</div>
</div>
</div>
</section>
<section id="get-the-scale-and-zero-point" class="level3">
<h3 class="anchored" data-anchor-id="get-the-scale-and-zero-point">Get the Scale and Zero-Point</h3>
<ul>
<li>s = (r_max-r_min)[current_tensor_range]/(q_max-q_min)[datatype_range]</li>
<li>z = int(round(q_min - r_min/s))</li>
<li>z and quantized tensor are of the same type</li>
<li>z is an integer because it represent zero(in the original ‘r’ range) with an integer in the quantized ‘q’ range</li>
<li>if z goes out of range:-
<ul>
<li>z &lt; q_min:-
<ul>
<li>z = q_min</li>
</ul></li>
<li>z &gt; q_max:-
<ul>
<li>z = q_max</li>
</ul></li>
</ul></li>
</ul>
<div id="91607687" class="cell" data-execution_count="2">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb2" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb2-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb2-2"></span>
<span id="cb2-3"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_q_scale_and_zero_point(tensor, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.int8):</span>
<span id="cb2-4">    </span>
<span id="cb2-5">    q_min, q_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.iinfo(dtype).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">min</span>, torch.iinfo(dtype).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">max</span></span>
<span id="cb2-6">    r_min, r_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> tensor.<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">min</span>().item(), tensor.<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">max</span>().item()</span>
<span id="cb2-7"></span>
<span id="cb2-8">    scale <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> (r_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> r_min) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span> (q_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> q_min)</span>
<span id="cb2-9"></span>
<span id="cb2-10">    zero_point <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> q_min <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> (r_min <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span> scale)</span>
<span id="cb2-11"></span>
<span id="cb2-12">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># clip the zero_point to fall in [quantized_min, quantized_max]</span></span>
<span id="cb2-13">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> zero_point <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">&lt;</span> q_min:</span>
<span id="cb2-14">        zero_point <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> q_min</span>
<span id="cb2-15">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">elif</span> zero_point <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">&gt;</span> q_max:</span>
<span id="cb2-16">        zero_point <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> q_max</span>
<span id="cb2-17">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span>:</span>
<span id="cb2-18">        <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># round and cast to int</span></span>
<span id="cb2-19">        zero_point <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">int</span>(<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">round</span>(zero_point))</span>
<span id="cb2-20">    </span>
<span id="cb2-21">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> scale, zero_point</span></code></pre></div></div>
</div>
</section>
<section id="symmetric-vs-asymmetric-mode" class="level3">
<h3 class="anchored" data-anchor-id="symmetric-vs-asymmetric-mode">Symmetric vs Asymmetric Mode</h3>
<ul>
<li>Asymmetric Mode:-
<ul>
<li>map [r_max, r_min] to [q_max, q_min]</li>
<li>This is what we have implemented above</li>
</ul></li>
<li>Symmetric Mode:-
<ul>
<li>map [-r_max, r_max] to [-q_max, q_max]
<ul>
<li>where r_max = max(|tensor|)</li>
</ul></li>
</ul></li>
</ul>
We don’t need to use zero point(z=0). this happens because the floating point range and the quantized range are symmetric with respect to zero
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/quantization-in-depth/im1.png" style="width:80%" class="figure-img">
<figcaption>
</figcaption>
</figure>
<p>Hence, we can simplify the equation to:-</p>
<ul>
<li>q = int(round(r/s))</li>
<li>s = r_max/q_max</li>
</ul>
<div id="da517ef8" class="cell" data-execution_count="3">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb3" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb3-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb3-2"></span>
<span id="cb3-3"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> get_q_scale_symmetric(tensor, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.int8):</span>
<span id="cb3-4">    r_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> tensor.<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">abs</span>().<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">max</span>().item()</span>
<span id="cb3-5">    q_max <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.iinfo(dtype).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">max</span></span>
<span id="cb3-6"></span>
<span id="cb3-7">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># return the scale</span></span>
<span id="cb3-8">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> r_max<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>q_max</span>
<span id="cb3-9"></span>
<span id="cb3-10"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> linear_q_symmetric(tensor, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.int8):</span>
<span id="cb3-11">    scale <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> get_q_scale_symmetric(tensor)</span>
<span id="cb3-12">    </span>
<span id="cb3-13">    quantized_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> linear_q_with_scale_and_zero_point(tensor,</span>
<span id="cb3-14">                                                     scale<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>scale,</span>
<span id="cb3-15">                   <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># in symmetric quantization zero point is = 0    </span></span>
<span id="cb3-16">                                                    zero_point<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>,</span>
<span id="cb3-17">                                                      dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>dtype)</span>
<span id="cb3-18">    </span>
<span id="cb3-19">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> quantized_tensor, scale</span></code></pre></div></div>
</div>
<p><strong>Trade-off</strong></p>
<ul>
<li><p>Utilization of quantized range:</p>
<ul>
<li>when using asymmetric quantization, the quantized range is fully utilized</li>
<li>When symmetric mode, if the float range is biased towards one side, this will result in a quantized range where a part of the range is dedicated to values that we’ll never see.(e.g ReLU where the output is positive)</li>
</ul></li>
<li><p>Simplicity:</p>
<ul>
<li>Symmetric mode is much simpler compared to asymmetric mode.</li>
</ul></li>
<li><p>Memory: We don’t have to store zero-point for symmetric quantization</p></li>
<li><p><strong>We use symmetric quantization for 8-bit, but as we go for lower bits such as 2 or 4 bits, we use asymmetric quantization</strong></p></li>
</ul>
</section>
<section id="finer-granularity-for-more-precision" class="level3">
<h3 class="anchored" data-anchor-id="finer-granularity-for-more-precision">Finer Granularity for more Precision</h3>
<ul>
<li>Different granularities
<ul>
<li>per tensor</li>
<li>per channel (along an axis)</li>
<li>per group (group n elements together)</li>
</ul></li>
<li>The more granular quantization is the more precise it will be.</li>
</ul>
</section>
<section id="per-channel-quantization" class="level3">
<h3 class="anchored" data-anchor-id="per-channel-quantization">Per Channel Quantization</h3>
<ul>
<li>we usually use per channel quantization in int8</li>
</ul>
<div id="66f89915" class="cell" data-execution_count="4">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb4" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb4-1"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> linear_q_symmetric_per_channel(r_tensor, dim, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.int8):</span>
<span id="cb4-2">    </span>
<span id="cb4-3">    output_dim <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> r_tensor.shape[dim]</span>
<span id="cb4-4">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># store the scales</span></span>
<span id="cb4-5">    scale <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.zeros(output_dim)</span>
<span id="cb4-6"></span>
<span id="cb4-7">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> index <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(output_dim):</span>
<span id="cb4-8">        sub_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> r_tensor.select(dim, index)</span>
<span id="cb4-9">        scale[index] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> get_q_scale_symmetric(sub_tensor, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>dtype)</span>
<span id="cb4-10"></span>
<span id="cb4-11">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># reshape the scale</span></span>
<span id="cb4-12">    scale_shape <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> [<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> r_tensor.dim()</span>
<span id="cb4-13">    scale_shape[dim] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span></span>
<span id="cb4-14">    scale <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> scale.view(scale_shape)</span>
<span id="cb4-15">    quantized_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> linear_q_with_scale_and_zero_point(</span>
<span id="cb4-16">        r_tensor, scale<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>scale, zero_point<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>dtype)</span>
<span id="cb4-17">   </span>
<span id="cb4-18">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> quantized_tensor, scale</span></code></pre></div></div>
</div>
</section>
<section id="per-group-quantization" class="level3">
<h3 class="anchored" data-anchor-id="per-group-quantization">Per Group Quantization</h3>
<ul>
<li><p>Group n(e.g.&nbsp;32, 64, 128) elements together and quantize</p></li>
<li><p>Per group quantization can require a lot of memory</p>
<ul>
<li>Let’s say we want to quantize a tensor in 4-bit and we choose group_size=32, symmetric mode(z=0), and we store the scales in FP16</li>
<li>It means that we actually quantizing the tensor in <strong>4.5 bits</strong> since we have:
<ul>
<li>4 bit(each element is stored in 4 bit)</li>
<li>16/32 bit (scale in 16 bits for every 32 elements)</li>
</ul></li>
</ul></li>
</ul>
<div id="eb39eb6d" class="cell" data-execution_count="5">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb5" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb5-1"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> linear_q_symmetric_per_group(tensor, group_size,</span>
<span id="cb5-2">                                 dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.int8):</span>
<span id="cb5-3">    </span>
<span id="cb5-4">    t_shape <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> tensor.shape</span>
<span id="cb5-5">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">assert</span> t_shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">%</span> group_size <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">==</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span></span>
<span id="cb5-6">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">assert</span> tensor.dim() <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">==</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span></span>
<span id="cb5-7">    </span>
<span id="cb5-8">    tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> tensor.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, group_size)</span>
<span id="cb5-9">    </span>
<span id="cb5-10">    quantized_tensor, scale <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> linear_q_symmetric_per_channel(</span>
<span id="cb5-11">                                tensor, dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>dtype)</span>
<span id="cb5-12">    </span>
<span id="cb5-13">    quantized_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> quantized_tensor.view(t_shape)</span>
<span id="cb5-14">    </span>
<span id="cb5-15">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> quantized_tensor, scale</span>
<span id="cb5-16"></span>
<span id="cb5-17"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> linear_dequantization_per_group(quantized_tensor, scale, </span>
<span id="cb5-18">                                    group_size):</span>
<span id="cb5-19">    </span>
<span id="cb5-20">    q_shape <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> quantized_tensor.shape</span>
<span id="cb5-21">    quantized_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> quantized_tensor.view(<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, group_size)</span>
<span id="cb5-22">    </span>
<span id="cb5-23">    dequantized_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> linear_dequantization(quantized_tensor, </span>
<span id="cb5-24">                                               scale, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>)</span>
<span id="cb5-25">    </span>
<span id="cb5-26">    dequantized_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> dequantized_tensor.view(q_shape)</span>
<span id="cb5-27">    </span>
<span id="cb5-28">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> dequantized_tensor</span></code></pre></div></div>
</div>
</section>
<section id="quantizing-weights-and-activations-for-inference" class="level3">
<h3 class="anchored" data-anchor-id="quantizing-weights-and-activations-for-inference">Quantizing Weights and Activations for Inference</h3>
<ul>
<li>Depending on what we quantize, the storage and the computation are not the same.</li>
<li>W8A32
<ul>
<li>If weights are quantized but not the activations, then computation is done floating point (FP16,FP32, BF16)</li>
<li>We need to dequantize the weights to perform the floating point computation (cast to float32)</li>
</ul></li>
<li>W8A8
<ul>
<li>Both are quantized</li>
<li>Computation is integer based but not <strong>supported by all hardware</strong></li>
</ul></li>
</ul>
</section>
<section id="custom-build-an-8-bit-quantizer" class="level3">
<h3 class="anchored" data-anchor-id="custom-build-an-8-bit-quantizer">Custom Build an 8-Bit Quantizer</h3>
<div id="c23e4d79" class="cell" data-execution_count="6">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb6" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb6-1"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">#W8A16LinearLayer</span></span>
<span id="cb6-2"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> w8_a16_forward(weight, <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">input</span>, scales, bias<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>):</span>
<span id="cb6-3">    </span>
<span id="cb6-4">    casted_weights <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> weight.to(<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">input</span>.dtype)</span>
<span id="cb6-5">    output <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> F.linear(<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">input</span>, casted_weights) <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> scales</span>
<span id="cb6-6">    </span>
<span id="cb6-7">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> bias <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">not</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>:</span>
<span id="cb6-8">        output <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> output <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+</span> bias</span>
<span id="cb6-9">      </span>
<span id="cb6-10">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> output</span></code></pre></div></div>
</div>
<div id="90db199e" class="cell" data-execution_count="7">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb7" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb7-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb7-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb7-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb7-4"></span>
<span id="cb7-5"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> W8A16LinearLayer(nn.Module):</span>
<span id="cb7-6">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, in_features, out_features, </span>
<span id="cb7-7">                 bias<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span>, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.float32):</span>
<span id="cb7-8">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb7-9">        </span>
<span id="cb7-10">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.int8_weights <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Parameter(torch.Tensor([<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>]</span>
<span id="cb7-11">                                     ).to(dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.int8))</span>
<span id="cb7-12"></span>
<span id="cb7-13"><span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">try</span>:</span>
<span id="cb7-14">    </span>
<span id="cb7-15">    W8A16LinearLayer(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb7-16">    </span>
<span id="cb7-17"><span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">except</span> <span class="pp" style="color: #AD0000;
background-color: null;
font-style: inherit;">Exception</span> <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> error:</span>
<span id="cb7-18">    <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span><span class="ch" style="color: #20794D;
background-color: null;
font-style: inherit;">\033</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">[91m"</span>, <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">type</span>(error).<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">__name__</span>, <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">": "</span>, error, <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span><span class="ch" style="color: #20794D;
background-color: null;
font-style: inherit;">\033</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">[0m"</span>)</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<div class="ansi-escaped-output">
<pre><span class="ansi-bright-red-fg"> RuntimeError :  Only Tensors of floating point and complex dtype can require gradients </span>
</pre>
</div>
</div>
</div>
<ul>
<li><p>When we create nn.Parameters, pytorch expects that parameter where it’s able to compute gradients on it.</p></li>
<li><p>The issue is that with PyTorch, you can’t explicitly compute gradients on INT8 tensors.</p></li>
<li><p>So above code snippet will give an error saying that only tensors of floating point and complex dtype can require gradients.</p></li>
<li><p>So the right approach to save INT8 weights is instead of saving attributes as being an endless parameter, is to call the method called register buffer.</p></li>
<li><p>This way instead of storing a parameter, we just store a buffer, meaning we don’t need to compute gradients on the tensor.</p></li>
<li><p>You can initialize it with whatever dtype you want.</p></li>
</ul>
<div id="e3917829" class="cell" data-execution_count="8">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb8" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb8-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb8-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb8-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb8-4"></span>
<span id="cb8-5"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> W8A16LinearLayer(nn.Module):</span>
<span id="cb8-6">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, in_features, out_features, </span>
<span id="cb8-7">                 bias<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span>, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.float32):</span>
<span id="cb8-8">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb8-9">        </span>
<span id="cb8-10">        </span>
<span id="cb8-11">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.register_buffer(</span>
<span id="cb8-12">            <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"int8_weights"</span>,</span>
<span id="cb8-13">            torch.randint(</span>
<span id="cb8-14">                <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">128</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">127</span>, (out_features, in_features), dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.int8</span>
<span id="cb8-15">            )</span>
<span id="cb8-16">        )</span>
<span id="cb8-17">        </span>
<span id="cb8-18">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.register_buffer(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"scales"</span>, </span>
<span id="cb8-19">                             torch.randn((out_features), dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>dtype)) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># We are interested in inference only</span></span>
<span id="cb8-20">        </span>
<span id="cb8-21">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> bias:</span>
<span id="cb8-22">            <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.register_buffer(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"bias"</span>, </span>
<span id="cb8-23">                                 torch.randn((<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, out_features), </span>
<span id="cb8-24">                                             dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>dtype))</span>
<span id="cb8-25">        </span>
<span id="cb8-26">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span>:</span>
<span id="cb8-27">            <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.bias <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span></span>
<span id="cb8-28">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> forward(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">input</span>):</span>
<span id="cb8-29">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> w8_a16_forward(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.int8_weights, </span>
<span id="cb8-30">                              <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">input</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.scales, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.bias)</span></code></pre></div></div>
</div>
<p><strong>Quantize a Base Model</strong></p>
<div id="550a1cb2" class="cell" data-execution_count="9">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb9" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb9-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb9-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb9-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb9-4"></span>
<span id="cb9-5"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> W8A16LinearLayer(nn.Module):</span>
<span id="cb9-6">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, in_features, out_features, </span>
<span id="cb9-7">                 bias<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span>, dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.float32):</span>
<span id="cb9-8">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb9-9">        </span>
<span id="cb9-10">        </span>
<span id="cb9-11">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.register_buffer(</span>
<span id="cb9-12">            <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"int8_weights"</span>,</span>
<span id="cb9-13">            torch.randint(</span>
<span id="cb9-14">                <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">128</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">127</span>, (out_features, in_features), dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.int8</span>
<span id="cb9-15">            )</span>
<span id="cb9-16">        )</span>
<span id="cb9-17">        </span>
<span id="cb9-18">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.register_buffer(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"scales"</span>, </span>
<span id="cb9-19">                             torch.randn((out_features), dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>dtype))</span>
<span id="cb9-20">        </span>
<span id="cb9-21">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> bias:</span>
<span id="cb9-22">            <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.register_buffer(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"bias"</span>, </span>
<span id="cb9-23">                                 torch.randn((<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, out_features), </span>
<span id="cb9-24">                                             dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>dtype))</span>
<span id="cb9-25">        </span>
<span id="cb9-26">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span>:</span>
<span id="cb9-27">            <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.bias <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span></span>
<span id="cb9-28"></span>
<span id="cb9-29">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> quantize(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, weights):</span>
<span id="cb9-30">        w_fp32 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> weights.clone().to(torch.float32)</span>
<span id="cb9-31"></span>
<span id="cb9-32">        scales <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> w_fp32.<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">abs</span>().<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">max</span>(dim<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=-</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>).values <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">127</span></span>
<span id="cb9-33">        scales <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> scales.to(weights.dtype)</span>
<span id="cb9-34"></span>
<span id="cb9-35">        int8_weights <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">round</span>(weights</span>
<span id="cb9-36">                        <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span>scales.unsqueeze(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)).to(torch.int8)</span>
<span id="cb9-37"></span>
<span id="cb9-38">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.int8_weights <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> int8_weights</span>
<span id="cb9-39">        <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.scales <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> scales</span>
<span id="cb9-40">    </span>
<span id="cb9-41">    <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> forward(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>, <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">input</span>):</span>
<span id="cb9-42">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> w8_a16_forward(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.int8_weights, </span>
<span id="cb9-43">                              <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">input</span>, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.scales, <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.bias)</span>
<span id="cb9-44"></span>
<span id="cb9-45">module <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> W8A16LinearLayer(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">4</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">8</span>)</span>
<span id="cb9-46"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Weights before:</span><span class="ch" style="color: #20794D;
background-color: null;
font-style: inherit;">\n</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span> , module.int8_weights)</span>
<span id="cb9-47">random_matrix <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.randn((<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">4</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">8</span>), dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.bfloat16)</span>
<span id="cb9-48">module.quantize(random_matrix)</span>
<span id="cb9-49"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Weights After:</span><span class="ch" style="color: #20794D;
background-color: null;
font-style: inherit;">\n</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span> , module.int8_weights)</span>
<span id="cb9-50"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Average quantization error:-"</span>,(random_matrix <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> module.int8_weights </span>
<span id="cb9-51"> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> module.scales.unsqueeze(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)).<span class="bu" style="color: null;
background-color: null;
font-style: inherit;">abs</span>().mean())</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<pre><code>Weights before:
 tensor([[ -87,  -38,  -15,  -74],
        [ 107,  -95,    7,  -94],
        [-112, -110,  -21,  122],
        [ 112,  107,  -87,  105],
        [  67,  -67,   78,   78],
        [ -26,   -9,  -92,  -26],
        [ 126,   -3,   12,   17],
        [  51,  -30,  -28,   33]], dtype=torch.int8)
Weights After:
 tensor([[  87,  -75,   90,  -69,  -16,   52,  127,   21],
        [  52,   12,  -86,   40,   66,  -44,  -82,  127],
        [-108, -115,  -70,   92, -116,  127,  -10,   61],
        [  88,   71, -106,   56,  -98, -127, -106,  -78]], dtype=torch.int8)
Average quantization error:- tensor(0.0020, dtype=torch.bfloat16)</code></pre>
</div>
</div>
</section>
<section id="replace-pytorch-layers-with-quantized-layers" class="level3">
<h3 class="anchored" data-anchor-id="replace-pytorch-layers-with-quantized-layers">Replace PyTorch layers with Quantized Layers</h3>
<ul>
<li>For language models, it better to not quantize the last layer.</li>
</ul>
<div id="36485cfa" class="cell" data-execution_count="10">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb11" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb11-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb11-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> nn</span>
<span id="cb11-3"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch.nn.functional <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">as</span> F</span>
<span id="cb11-4"></span>
<span id="cb11-5"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> replace_linear_with_target(module, </span>
<span id="cb11-6">                               target_class, module_name_to_exclude):</span>
<span id="cb11-7">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> name, child <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> module.named_children():</span>
<span id="cb11-8">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">isinstance</span>(child, nn.Linear) <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">and</span> <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">not</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">\</span></span>
<span id="cb11-9">          <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">any</span>([x <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">==</span> name <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> x <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> module_name_to_exclude]):</span>
<span id="cb11-10">            old_bias <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> child.bias</span>
<span id="cb11-11"></span>
<span id="cb11-12">            new_module <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> target_class(child.in_features, </span>
<span id="cb11-13">                                      child.out_features, </span>
<span id="cb11-14">                                      old_bias <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">not</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>, </span>
<span id="cb11-15">                                      child.weight.dtype)</span>
<span id="cb11-16">            <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">setattr</span>(module, name, new_module)</span>
<span id="cb11-17">            <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> old_bias <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">not</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>:</span>
<span id="cb11-18">              <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">getattr</span>(module, name).bias <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> old_bias</span>
<span id="cb11-19">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span>:</span>
<span id="cb11-20">            <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Recursively call the function for nested modules</span></span>
<span id="cb11-21">            replace_linear_with_target(</span>
<span id="cb11-22">                child, target_class, module_name_to_exclude)</span>
<span id="cb11-23"></span>
<span id="cb11-24"></span>
<span id="cb11-25"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> replace_linear_with_target_and_quantize(module, </span>
<span id="cb11-26">                               target_class, module_name_to_exclude):</span>
<span id="cb11-27">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> name, child <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> module.named_children():</span>
<span id="cb11-28">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">isinstance</span>(child, nn.Linear) <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">and</span> <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">not</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">\</span></span>
<span id="cb11-29">        <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">any</span>([x <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">==</span> name <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> x <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> module_name_to_exclude]):</span>
<span id="cb11-30">            old_bias <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> child.bias</span>
<span id="cb11-31">            old_weight <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> child.weight</span>
<span id="cb11-32"></span>
<span id="cb11-33">            new_module <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> target_class(child.in_features, </span>
<span id="cb11-34">                                      child.out_features, </span>
<span id="cb11-35">                                      old_bias <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">not</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>, </span>
<span id="cb11-36">                                      child.weight.dtype)</span>
<span id="cb11-37">            <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">setattr</span>(module, name, new_module) <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># current module is replaced by new_module</span></span>
<span id="cb11-38"></span>
<span id="cb11-39">            <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">getattr</span>(module, name).quantize(old_weight)</span>
<span id="cb11-40">            </span>
<span id="cb11-41">            <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> old_bias <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">is</span> <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">not</span> <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">None</span>:</span>
<span id="cb11-42">              <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">getattr</span>(module, name).bias <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> old_bias</span>
<span id="cb11-43">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">else</span>:</span>
<span id="cb11-44">            <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Recursively call the function for nested modules</span></span>
<span id="cb11-45">            replace_linear_with_target_and_quantize(child, </span>
<span id="cb11-46">                     target_class, module_name_to_exclude)</span>
<span id="cb11-47"></span>
<span id="cb11-48"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">class</span> DummyModel(torch.nn.Module):</span>
<span id="cb11-49">  <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> <span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>(<span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>):</span>
<span id="cb11-50">    <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">super</span>().<span class="fu" style="color: #4758AB;
background-color: null;
font-style: inherit;">__init__</span>()</span>
<span id="cb11-51">    <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.emb <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.nn.Embedding(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb11-52">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Try with bias</span></span>
<span id="cb11-53">    <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.linear_1 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>)</span>
<span id="cb11-54">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Try without bias</span></span>
<span id="cb11-55">    <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.linear_2 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, bias<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>)</span>
<span id="cb11-56">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Lm prediction head</span></span>
<span id="cb11-57">    <span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">self</span>.lm_head <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> nn.Linear(<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, bias<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>)</span>
<span id="cb11-58"></span>
<span id="cb11-59">model_1 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> DummyModel()</span>
<span id="cb11-60">model_2 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> DummyModel()</span>
<span id="cb11-61">replace_linear_with_target_and_quantize(model_1, W8A16LinearLayer, [<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"lm_head"</span>])</span>
<span id="cb11-62"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"model_1"</span>,model_1)</span>
<span id="cb11-63"></span>
<span id="cb11-64">replace_linear_with_target_and_quantize(model_2, W8A16LinearLayer, [])</span>
<span id="cb11-65"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"model_2"</span>,model_2)</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<pre><code>model_1 DummyModel(
  (emb): Embedding(1, 1)
  (linear_1): W8A16LinearLayer()
  (linear_2): W8A16LinearLayer()
  (lm_head): Linear(in_features=1, out_features=1, bias=False)
)
model_2 DummyModel(
  (emb): Embedding(1, 1)
  (linear_1): W8A16LinearLayer()
  (linear_2): W8A16LinearLayer()
  (lm_head): W8A16LinearLayer()
)</code></pre>
</div>
</div>
</section>
<section id="quantize-any-open-source-pytorch-model" class="level3">
<h3 class="anchored" data-anchor-id="quantize-any-open-source-pytorch-model">Quantize any Open Source PyTorch Model</h3>
<div id="c468be01" class="cell" data-execution_count="11">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb13" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb13-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">from</span> transformers <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> AutoModelForCausalLM, AutoTokenizer, pipeline</span>
<span id="cb13-2"></span>
<span id="cb13-3">model_id <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Salesforce/codegen-350M-mono"</span></span>
<span id="cb13-4"></span>
<span id="cb13-5">model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> AutoModelForCausalLM.from_pretrained(model_id, </span>
<span id="cb13-6">                                    torch_dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.bfloat16, </span>
<span id="cb13-7">                                             low_cpu_mem_usage<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span>)</span>
<span id="cb13-8">tokenizer <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> AutoTokenizer.from_pretrained(model_id)</span>
<span id="cb13-9"></span>
<span id="cb13-10">pipe <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> pipeline(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"text-generation"</span>, model<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>model, tokenizer<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>tokenizer)</span>
<span id="cb13-11"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(pipe(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"def hello_world():"</span>, max_new_tokens<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">20</span>, do_sample<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>)[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>][<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"generated_text"</span>])</span>
<span id="cb13-12"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Model before:</span><span class="ch" style="color: #20794D;
background-color: null;
font-style: inherit;">\n\n</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>, model)</span>
<span id="cb13-13">replace_linear_with_target_and_quantize(model, </span>
<span id="cb13-14">                                        W8A16LinearLayer, [<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"lm_head"</span>])</span>
<span id="cb13-15"></span>
<span id="cb13-16"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Model after:</span><span class="ch" style="color: #20794D;
background-color: null;
font-style: inherit;">\n\n</span><span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>, model)</span>
<span id="cb13-17"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(pipe(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"def hello_world():"</span>, max_new_tokens<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">20</span>, </span>
<span id="cb13-18">           do_sample<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">False</span>)[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>][<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"generated_text"</span>])</span></code></pre></div></div>
<div class="cell-output cell-output-stderr">
<pre><code>Setting `pad_token_id` to `eos_token_id`:50256 for open-end generation.</code></pre>
</div>
<div class="cell-output cell-output-stdout">
<pre><code>def hello_world():
    print("Hello World")

hello_world()

# 파
Model before:

 CodeGenForCausalLM(
  (transformer): CodeGenModel(
    (wte): Embedding(51200, 1024)
    (drop): Dropout(p=0.0, inplace=False)
    (h): ModuleList(
      (0-19): 20 x CodeGenBlock(
        (ln_1): LayerNorm((1024,), eps=1e-05, elementwise_affine=True)
        (attn): CodeGenAttention(
          (attn_dropout): Dropout(p=0.0, inplace=False)
          (resid_dropout): Dropout(p=0.0, inplace=False)
          (qkv_proj): Linear(in_features=1024, out_features=3072, bias=False)
          (out_proj): Linear(in_features=1024, out_features=1024, bias=False)
        )
        (mlp): CodeGenMLP(
          (fc_in): Linear(in_features=1024, out_features=4096, bias=True)
          (fc_out): Linear(in_features=4096, out_features=1024, bias=True)
          (act): NewGELUActivation()
          (dropout): Dropout(p=0.0, inplace=False)
        )
      )
    )
    (ln_f): LayerNorm((1024,), eps=1e-05, elementwise_affine=True)
  )
  (lm_head): Linear(in_features=1024, out_features=51200, bias=True)
)</code></pre>
</div>
<div class="cell-output cell-output-stderr">
<pre><code>Setting `pad_token_id` to `eos_token_id`:50256 for open-end generation.</code></pre>
</div>
<div class="cell-output cell-output-stdout">
<pre><code>Model after:

 CodeGenForCausalLM(
  (transformer): CodeGenModel(
    (wte): Embedding(51200, 1024)
    (drop): Dropout(p=0.0, inplace=False)
    (h): ModuleList(
      (0-19): 20 x CodeGenBlock(
        (ln_1): LayerNorm((1024,), eps=1e-05, elementwise_affine=True)
        (attn): CodeGenAttention(
          (attn_dropout): Dropout(p=0.0, inplace=False)
          (resid_dropout): Dropout(p=0.0, inplace=False)
          (qkv_proj): W8A16LinearLayer()
          (out_proj): W8A16LinearLayer()
        )
        (mlp): CodeGenMLP(
          (fc_in): W8A16LinearLayer()
          (fc_out): W8A16LinearLayer()
          (act): NewGELUActivation()
          (dropout): Dropout(p=0.0, inplace=False)
        )
      )
    )
    (ln_f): LayerNorm((1024,), eps=1e-05, elementwise_affine=True)
  )
  (lm_head): Linear(in_features=1024, out_features=51200, bias=True)
)
def hello_world():
    print("Hello World")

# hello_world()

# def hello_</code></pre>
</div>
</div>
<ul>
<li>Above code snippet modifies the model inplace</li>
<li>Also don’t try to change the lm_head otherwise it will not give the desired results</li>
<li>All the rounding errors can sum up once you start generating a lot of tokens, until may be all of these errors get super large so that it affects the model’s performance</li>
</ul>
</section>
<section id="load-your-quantized-weights-from-huggingface-hub" class="level3">
<h3 class="anchored" data-anchor-id="load-your-quantized-weights-from-huggingface-hub">Load your Quantized Weights from HuggingFace Hub</h3>
<ul>
<li>The idea is to quantize weights on bigger instance and then push it back to huggingface. So that we don’t have to load and quantize again and again.</li>
<li>Then use meta device from pytorch to load the skeleton of the model instead of loading the whole model itself.</li>
<li>Replace the original layers with the quantized layers</li>
<li>Load the quantized weights from huggingfacehub</li>
</ul>
<div id="af744858" class="cell" data-execution_count="12">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb18" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb18-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb18-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">from</span> transformers <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> AutoModelForCausalLM, AutoTokenizer</span>
<span id="cb18-3"></span>
<span id="cb18-4">model_id <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"facebook/opt-125m"</span></span>
<span id="cb18-5"></span>
<span id="cb18-6">model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> AutoModelForCausalLM.from_pretrained(</span>
<span id="cb18-7">    model_id, torch_dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.bfloat16, low_cpu_mem_usage<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span>)</span>
<span id="cb18-8">tokenizer <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> AutoTokenizer.from_pretrained(model_id)</span>
<span id="cb18-9"></span>
<span id="cb18-10">replace_linear_with_target_and_quantize(model, </span>
<span id="cb18-11">                             W8A16LinearLayer, </span>
<span id="cb18-12">                                   [<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"lm_head"</span>])</span>
<span id="cb18-13"></span>
<span id="cb18-14">model</span>
<span id="cb18-15"></span>
<span id="cb18-16">quantized_state_dict <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> model.state_dict()</span>
<span id="cb18-17">torch.save(quantized_state_dict, <span class="vs" style="color: #20794D;
background-color: null;
font-style: inherit;">r"/home/ritesh/github_repos/riteshrm</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">.</span><span class="vs" style="color: #20794D;
background-color: null;
font-style: inherit;">github</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">.</span><span class="vs" style="color: #20794D;
background-color: null;
font-style: inherit;">io/tmp/quantized_state_dict</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">.</span><span class="vs" style="color: #20794D;
background-color: null;
font-style: inherit;">pth"</span>)</span></code></pre></div></div>
</div>
<p><strong>How to upload on HF</strong></p>
<p>from huggingface_hub import HfApi, create_repo</p>
<p>YOUR_HF_USERNAME = “” your_repo_id = f”{YOUR_HF_USERNAME}/opt-125m-quantized-dlai”</p>
<p>api = HfApi()</p>
<p>create_repo(your_repo_id)</p>
<p>api.upload_file( path_or_fileobj=“quantized_state_dict.pth”, path_in_repo=“quantized_state_dict.pth”, repo_id=your_repo_id )</p>
<div id="aceb298f" class="cell" data-execution_count="13">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb19" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb19-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb19-2"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">from</span> transformers <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> OPTForCausalLM, AutoTokenizer, AutoConfig</span>
<span id="cb19-3"></span>
<span id="cb19-4">model_id <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"facebook/opt-125m"</span></span>
<span id="cb19-5">config <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> AutoConfig.from_pretrained(model_id)</span>
<span id="cb19-6"></span>
<span id="cb19-7"><span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">with</span> torch.device(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"meta"</span>):</span>
<span id="cb19-8">  model <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> OPTForCausalLM(config)</span>
<span id="cb19-9"></span>
<span id="cb19-10">tokenizer <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> AutoTokenizer.from_pretrained(model_id)</span>
<span id="cb19-11"></span>
<span id="cb19-12"><span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> param <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> model.parameters():</span>
<span id="cb19-13">  <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(param)</span>
<span id="cb19-14">  <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">break</span></span></code></pre></div></div>
<div class="cell-output cell-output-stderr">
<pre><code>/home/ritesh/miniconda3/envs/quarto/lib/python3.10/site-packages/huggingface_hub/file_download.py:942: FutureWarning: `resume_download` is deprecated and will be removed in version 1.0.0. Downloads always resume when possible. If you want to force a new download, use `force_download=True`.
  warnings.warn(</code></pre>
</div>
<div class="cell-output cell-output-stdout">
<pre><code>Parameter containing:
tensor(..., device='meta', size=(50272, 768), requires_grad=True)</code></pre>
</div>
</div>
<div id="2779f144" class="cell" data-execution_count="14">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb22" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb22-1">model</span></code></pre></div></div>
<div class="cell-output cell-output-display" data-execution_count="14">
<pre><code>OPTForCausalLM(
  (model): OPTModel(
    (decoder): OPTDecoder(
      (embed_tokens): Embedding(50272, 768, padding_idx=1)
      (embed_positions): OPTLearnedPositionalEmbedding(2050, 768)
      (final_layer_norm): LayerNorm((768,), eps=1e-05, elementwise_affine=True)
      (layers): ModuleList(
        (0-11): 12 x OPTDecoderLayer(
          (self_attn): OPTAttention(
            (k_proj): Linear(in_features=768, out_features=768, bias=True)
            (v_proj): Linear(in_features=768, out_features=768, bias=True)
            (q_proj): Linear(in_features=768, out_features=768, bias=True)
            (out_proj): Linear(in_features=768, out_features=768, bias=True)
          )
          (activation_fn): ReLU()
          (self_attn_layer_norm): LayerNorm((768,), eps=1e-05, elementwise_affine=True)
          (fc1): Linear(in_features=768, out_features=3072, bias=True)
          (fc2): Linear(in_features=3072, out_features=768, bias=True)
          (final_layer_norm): LayerNorm((768,), eps=1e-05, elementwise_affine=True)
        )
      )
    )
  )
  (lm_head): Linear(in_features=768, out_features=50272, bias=False)
)</code></pre>
</div>
</div>
<div id="aaaefa51" class="cell" data-execution_count="15">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb24" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb24-1">replace_linear_with_target(model, W8A16LinearLayer, [<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"lm_head"</span>])</span>
<span id="cb24-2">model</span></code></pre></div></div>
<div class="cell-output cell-output-display" data-execution_count="15">
<pre><code>OPTForCausalLM(
  (model): OPTModel(
    (decoder): OPTDecoder(
      (embed_tokens): Embedding(50272, 768, padding_idx=1)
      (embed_positions): OPTLearnedPositionalEmbedding(2050, 768)
      (final_layer_norm): LayerNorm((768,), eps=1e-05, elementwise_affine=True)
      (layers): ModuleList(
        (0-11): 12 x OPTDecoderLayer(
          (self_attn): OPTAttention(
            (k_proj): W8A16LinearLayer()
            (v_proj): W8A16LinearLayer()
            (q_proj): W8A16LinearLayer()
            (out_proj): W8A16LinearLayer()
          )
          (activation_fn): ReLU()
          (self_attn_layer_norm): LayerNorm((768,), eps=1e-05, elementwise_affine=True)
          (fc1): W8A16LinearLayer()
          (fc2): W8A16LinearLayer()
          (final_layer_norm): LayerNorm((768,), eps=1e-05, elementwise_affine=True)
        )
      )
    )
  )
  (lm_head): Linear(in_features=768, out_features=50272, bias=False)
)</code></pre>
</div>
</div>
<p><strong>If loading from HF</strong></p>
<p>from huggingface_hub import hf_hub_download</p>
<p>state_dict_cache_path = hf_hub_download( “ybelkada/opt-125m-quantized-dlai”, “quantized_state_dict.pth” )</p>
<div id="5d04144c" class="cell" data-execution_count="16">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb26" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb26-1">state_dict <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.load(<span class="vs" style="color: #20794D;
background-color: null;
font-style: inherit;">r"/home/ritesh/github_repos/riteshrm</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">.</span><span class="vs" style="color: #20794D;
background-color: null;
font-style: inherit;">github</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">.</span><span class="vs" style="color: #20794D;
background-color: null;
font-style: inherit;">io/tmp/quantized_state_dict</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">.</span><span class="vs" style="color: #20794D;
background-color: null;
font-style: inherit;">pth"</span>)</span>
<span id="cb26-2">model.load_state_dict(state_dict, strict<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span>, assign<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="va" style="color: #111111;
background-color: null;
font-style: inherit;">True</span>)</span></code></pre></div></div>
<div class="cell-output cell-output-stderr">
<pre><code>/tmp/ipykernel_1365/1695582919.py:1: FutureWarning: You are using `torch.load` with `weights_only=False` (the current default value), which uses the default pickle module implicitly. It is possible to construct malicious pickle data which will execute arbitrary code during unpickling (See https://github.com/pytorch/pytorch/blob/main/SECURITY.md#untrusted-models for more details). In a future release, the default value for `weights_only` will be flipped to `True`. This limits the functions that could be executed during unpickling. Arbitrary objects will no longer be allowed to be loaded via this mode unless they are explicitly allowlisted by the user via `torch.serialization.add_safe_globals`. We recommend you start setting `weights_only=True` for any use case where you don't have full control of the loaded file. Please open an issue on GitHub for any issues related to this experimental feature.
  state_dict = torch.load(r"/home/ritesh/github_repos/riteshrm.github.io/tmp/quantized_state_dict.pth")</code></pre>
</div>
<div class="cell-output cell-output-display" data-execution_count="16">
<pre><code>&lt;All keys matched successfully&gt;</code></pre>
</div>
</div>
<div id="de45a068" class="cell" data-execution_count="17">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb29" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb29-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">from</span> transformers <span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> pipeline</span>
<span id="cb29-2"></span>
<span id="cb29-3">pipe <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> pipeline(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"text-generation"</span>, model<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>model, tokenizer<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>tokenizer)</span>
<span id="cb29-4">pipe(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Hello today I am"</span>, max_new_tokens<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">40</span>)</span>
<span id="cb29-5"></span>
<span id="cb29-6">pipe <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> pipeline(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"text-generation"</span>, model<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>model, tokenizer<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>tokenizer)</span>
<span id="cb29-7">pipe(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"Hello today I am giving a course about"</span>, max_new_tokens<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">10</span>)</span></code></pre></div></div>
<div class="cell-output cell-output-display" data-execution_count="17">
<pre><code>[{'generated_text': "Hello today I am giving a course about the history of the world's first ever solar eclipse"}]</code></pre>
</div>
</div>
</section>
<section id="weights-packing" class="level3">
<h3 class="anchored" data-anchor-id="weights-packing">Weights Packing</h3>
<ul>
<li>Weights packing is important for storing quantized weights, because torch.int4 is not available as of today, so we need to store and load the weights in int8</li>
<li>This is not ideal because:
<ul>
<li>tensor will occupy 8-bit per datapoint and might add a considerable overhead for large models</li>
<li>There would be no point of quantizing to 2/4 bits because we are still using 8-bit</li>
</ul></li>
<li>So, we need to pack values</li>
<li>Consider a tensor with 4 values each with 2-bit(0,1,2,3) precision but stored in 8-bit
<ul>
<li>tensor = torch.tensor([1,0,3,2], dtype=torch.uint8)</li>
<li>1:- 00000001</li>
<li>0:- 00000000</li>
<li>3:- 00000011</li>
<li>2:- 00000010</li>
</ul></li>
<li>We can pack all these values into a single 8-bit value as 177
<ul>
<li>177:- 10110001</li>
</ul></li>
<li>Advantages:-
<ul>
<li>It reflects the true memory footprint of the quantized weights Disadvantages:-</li>
<li>The unpacked tensors need to be a shape with a multiple of 8//nbits</li>
<li>It needs to unpack before performing an operation</li>
</ul></li>
</ul>
</section>
<section id="packing-2-bit-weights" class="level3">
<h3 class="anchored" data-anchor-id="packing-2-bit-weights">Packing 2-bit Weights</h3>
<div id="205d9836" class="cell" data-execution_count="18">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb31" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb31-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb31-2"></span>
<span id="cb31-3"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Example Tensor: [1, 0, 3, 2]</span></span>
<span id="cb31-4">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 1 0 3 2 - 01 00 11 10</span></span>
<span id="cb31-5"></span>
<span id="cb31-6">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Starting point of packed int8 Tensor</span></span>
<span id="cb31-7">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [0000 0000]</span></span>
<span id="cb31-8"></span>
<span id="cb31-9">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### First Iteration Start:</span></span>
<span id="cb31-10">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor State: [0000 0000]</span></span>
<span id="cb31-11">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 1 = 0000 0001</span></span>
<span id="cb31-12">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0000 0001</span></span>
<span id="cb31-13">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># No left shifts in the First Iteration</span></span>
<span id="cb31-14">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># After bit-wise OR operation between 0000 0000 and 0000 0001:</span></span>
<span id="cb31-15">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor State: 0000 0001</span></span>
<span id="cb31-16">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### First Iteration End</span></span>
<span id="cb31-17"></span>
<span id="cb31-18">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Second Iteration Start:</span></span>
<span id="cb31-19">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor State: [0000 0001]</span></span>
<span id="cb31-20">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0 = 0000 0000</span></span>
<span id="cb31-21">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0000 0000</span></span>
<span id="cb31-22">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 2 left shifts:</span></span>
<span id="cb31-23">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [0000 0000] (1 shift)-&gt; 0000 0000 (2 shift)-&gt; 0000 0000</span></span>
<span id="cb31-24">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># After bit-wise OR operation between 0000 0001 and 0000 0000:</span></span>
<span id="cb31-25">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor State: 0000 0001</span></span>
<span id="cb31-26">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Second Iteration End</span></span>
<span id="cb31-27"></span>
<span id="cb31-28">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Third Iteration Start:</span></span>
<span id="cb31-29">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor State: [0000 0001]</span></span>
<span id="cb31-30">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 3 = 0000 0011</span></span>
<span id="cb31-31">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0000 0011</span></span>
<span id="cb31-32">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 4 left shifts:</span></span>
<span id="cb31-33">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [0000 0011] (1 shift)-&gt; 0000 0110 (2 shift)-&gt; 0000 1100</span></span>
<span id="cb31-34">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0000 1100 (3 shift)-&gt; 0001 1000 (4 shift)-&gt; 0011 0000</span></span>
<span id="cb31-35">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># After bit-wise OR operation between 0000 0001 and 0011 0000:</span></span>
<span id="cb31-36">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor State: 0011 0001</span></span>
<span id="cb31-37">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Third Iteration End</span></span>
<span id="cb31-38"></span>
<span id="cb31-39">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Fourth Iteration Start:</span></span>
<span id="cb31-40">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor State: [0011 0001]</span></span>
<span id="cb31-41">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 2 = 0000 0010</span></span>
<span id="cb31-42">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0000 0010</span></span>
<span id="cb31-43">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 6 left shifts:</span></span>
<span id="cb31-44">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [0000 0010] (1 shift)-&gt; 0000 0100 (2 shift)-&gt; 0000 1000</span></span>
<span id="cb31-45">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0000 1000 (3 shift)-&gt; 0001 0000 (4 shift)-&gt; 0010 0000</span></span>
<span id="cb31-46">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0010 0000 (5 shift)-&gt; 0100 0000 (6 shift)-&gt; 1000 0000</span></span>
<span id="cb31-47">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># After bit-wise OR operation between 0011 0001 and 1000 0000:</span></span>
<span id="cb31-48">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor State: 1011 0001</span></span>
<span id="cb31-49">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Fourth Iteration End</span></span>
<span id="cb31-50"></span>
<span id="cb31-51">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Final packed int8 Tensor State: [1011 0001]</span></span>
<span id="cb31-52"></span>
<span id="cb31-53"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> pack_weights(uint8tensor, bits):</span>
<span id="cb31-54">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">if</span> uint8tensor.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> bits <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">%</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">8</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">!=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>:</span>
<span id="cb31-55">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">raise</span> <span class="pp" style="color: #AD0000;
background-color: null;
font-style: inherit;">ValueError</span>(<span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">f"The input shape needs to be a multiple </span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">\</span></span>
<span id="cb31-56"><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">        of </span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">8</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span> bits<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;"> - got </span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span>uint8tensor<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">.</span>shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>]<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>)</span>
<span id="cb31-57"></span>
<span id="cb31-58">    num_values <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> uint8tensor.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> bits <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">8</span></span>
<span id="cb31-59"></span>
<span id="cb31-60">    num_steps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">8</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span> bits</span>
<span id="cb31-61"></span>
<span id="cb31-62">    unpacked_idx <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span></span>
<span id="cb31-63"></span>
<span id="cb31-64">    packed_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.zeros((num_values), dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.uint8)</span>
<span id="cb31-65"></span>
<span id="cb31-66">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 1 0 3 2 - 01 00 11 10</span></span>
<span id="cb31-67"></span>
<span id="cb31-68">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [0000 0000] -&gt; 0000 0001</span></span>
<span id="cb31-69"></span>
<span id="cb31-70">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0000 0001</span></span>
<span id="cb31-71"></span>
<span id="cb31-72">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0000 0000 - 0000 0000</span></span>
<span id="cb31-73"></span>
<span id="cb31-74">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 0000 0011 - 0011 0000 - 0011 0001</span></span>
<span id="cb31-75"></span>
<span id="cb31-76">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 1011 0001</span></span>
<span id="cb31-77">    </span>
<span id="cb31-78">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(num_values):</span>
<span id="cb31-79">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> j <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(num_steps):</span>
<span id="cb31-80">            packed_tensor[i] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">|=</span> uint8tensor[unpacked_idx] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">&lt;&lt;</span> (bits <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> j)</span>
<span id="cb31-81">            unpacked_idx <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span></span>
<span id="cb31-82">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> packed_tensor</span>
<span id="cb31-83">unpacked_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor([<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>], </span>
<span id="cb31-84">                               dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.uint8)</span>
<span id="cb31-85">pack_weights(unpacked_tensor, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>)</span>
<span id="cb31-86">unpacked_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor([<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span>], </span>
<span id="cb31-87">                               dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.uint8)</span>
<span id="cb31-88">pack_weights(unpacked_tensor, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>)</span></code></pre></div></div>
<div class="cell-output cell-output-display" data-execution_count="18">
<pre><code>tensor([177, 255], dtype=torch.uint8)</code></pre>
</div>
</div>
</section>
<section id="unpacking-2-bit-weights" class="level3">
<h3 class="anchored" data-anchor-id="unpacking-2-bit-weights">Unpacking 2-Bit Weights</h3>
<div id="0f3cd745" class="cell" data-execution_count="19">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb33" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb33-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb33-2"></span>
<span id="cb33-3"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Example Tensor: [10110001]</span></span>
<span id="cb33-4">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Which was Originally: 1 0 3 2 - 01 00 11 10</span></span>
<span id="cb33-5"></span>
<span id="cb33-6">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Starting point of unpacked Tensor</span></span>
<span id="cb33-7">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [00000000 00000000 00000000 00000000]</span></span>
<span id="cb33-8"></span>
<span id="cb33-9">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### First Iteration Start:</span></span>
<span id="cb33-10">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor: [10110001]</span></span>
<span id="cb33-11">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># You want to extract 01 from [101100 01]</span></span>
<span id="cb33-12">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># No right shifts in the First Iteration</span></span>
<span id="cb33-13">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># After bit-wise OR operation between 00000000 and 10110001:</span></span>
<span id="cb33-14">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [10110001 00000000 00000000 00000000]</span></span>
<span id="cb33-15">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># unpacked Tensor state: [10110001 00000000 00000000 00000000]</span></span>
<span id="cb33-16">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### First Iteration End</span></span>
<span id="cb33-17"></span>
<span id="cb33-18">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Second Iteration Start:</span></span>
<span id="cb33-19">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor: [10110001]</span></span>
<span id="cb33-20">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># You want to extract 00 from [1011 00 01]</span></span>
<span id="cb33-21">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 2 right shifts:</span></span>
<span id="cb33-22">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [10110001] (1 shift)-&gt; 01011000 (2 shift)-&gt; 00101100</span></span>
<span id="cb33-23">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># After bit-wise OR operation between 00000000 and 00101100:</span></span>
<span id="cb33-24">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [10110001 00101100 00000000 00000000]</span></span>
<span id="cb33-25">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># unpacked Tensor state: [10110001 00101100 00000000 00000000]</span></span>
<span id="cb33-26">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Second Iteration End</span></span>
<span id="cb33-27"></span>
<span id="cb33-28">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Third Iteration Start:</span></span>
<span id="cb33-29">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor: [10110001]</span></span>
<span id="cb33-30">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># You want to extract 11 from [10 11 0001]</span></span>
<span id="cb33-31">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 4 right shifts:</span></span>
<span id="cb33-32">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [10110001] (1 shift)-&gt; 01011000 (2 shift)-&gt; 00101100</span></span>
<span id="cb33-33">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 00101100 (3 shift)-&gt; 00010110 (4 shift)-&gt; 00001011</span></span>
<span id="cb33-34">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># After bit-wise OR operation between 00000000 and 00001011:</span></span>
<span id="cb33-35">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [10110001 00101100 00001011 00000000]</span></span>
<span id="cb33-36">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># unpacked Tensor state: [10110001 00101100 00001011 00000000]</span></span>
<span id="cb33-37">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Third Iteration End</span></span>
<span id="cb33-38"></span>
<span id="cb33-39">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Fourth Iteration Start:</span></span>
<span id="cb33-40">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># packed int8 Tensor: [10110001]</span></span>
<span id="cb33-41">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># You want to extract 10 from [10 110001]</span></span>
<span id="cb33-42">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 6 right shifts:</span></span>
<span id="cb33-43">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [10110001] (1 shift)-&gt; 01011000 (2 shift)-&gt; 00101100</span></span>
<span id="cb33-44">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 00101100 (3 shift)-&gt; 00010110 (4 shift)-&gt; 00001011</span></span>
<span id="cb33-45">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 00001011 (5 shift)-&gt; 00000101 (6 shift)-&gt; 00000010</span></span>
<span id="cb33-46">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># After bit-wise OR operation between 00000000 and 00000010:</span></span>
<span id="cb33-47">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [10110001 00101100 00001011 00000010]</span></span>
<span id="cb33-48">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># unpacked Tensor state: [10110001 00101100 00001011 00000010]</span></span>
<span id="cb33-49">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">##### Fourth Iteration End</span></span>
<span id="cb33-50"></span>
<span id="cb33-51">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Last step: Perform masking (bit-wise AND operation)</span></span>
<span id="cb33-52">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Mask: 00000011</span></span>
<span id="cb33-53">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Bit-wise AND operation between </span></span>
<span id="cb33-54">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># unpacked Tensor and 00000011</span></span>
<span id="cb33-55">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [10110001 00101100 00001011 00000010] &lt;- unpacked tensor</span></span>
<span id="cb33-56">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [00000011 00000011 00000011 00000011] &lt;- Mask</span></span>
<span id="cb33-57">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [00000001 00000000 00000011 00000010] &lt;- Result</span></span>
<span id="cb33-58"></span>
<span id="cb33-59">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Final</span></span>
<span id="cb33-60">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># unpacked Tensor state: [00000001 00000000 00000011 00000010]</span></span>
<span id="cb33-61"></span>
<span id="cb33-62"><span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">def</span> unpack_weights(uint8tensor, bits):</span>
<span id="cb33-63">    num_values <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> uint8tensor.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">8</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span> bits</span>
<span id="cb33-64"></span>
<span id="cb33-65">    num_steps <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">8</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">//</span> bits</span>
<span id="cb33-66"></span>
<span id="cb33-67">    unpacked_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.zeros((num_values), dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.uint8)</span>
<span id="cb33-68"></span>
<span id="cb33-69">    unpacked_idx <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span></span>
<span id="cb33-70"></span>
<span id="cb33-71">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 1 0 3 2 - 01 00 11 10</span></span>
<span id="cb33-72"></span>
<span id="cb33-73">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [00000000 00000000 00000000 00000000]</span></span>
<span id="cb33-74">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [10110001 00101100 00001011 00000010]</span></span>
<span id="cb33-75">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># [00000001 00000000 00000011 00000010]</span></span>
<span id="cb33-76"></span>
<span id="cb33-77">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 10110001</span></span>
<span id="cb33-78">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 00000011</span></span>
<span id="cb33-79">    </span>
<span id="cb33-80">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 00000001</span></span>
<span id="cb33-81"></span>
<span id="cb33-82">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 1: [10110001]</span></span>
<span id="cb33-83">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 2: [00101100]</span></span>
<span id="cb33-84">    <span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># 3: [00001011]</span></span>
<span id="cb33-85"></span>
<span id="cb33-86">    mask <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span> <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">**</span> bits <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">-</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span></span>
<span id="cb33-87"></span>
<span id="cb33-88">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> i <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(uint8tensor.shape[<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">0</span>]):</span>
<span id="cb33-89">        <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">for</span> j <span class="kw" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">in</span> <span class="bu" style="color: null;
background-color: null;
font-style: inherit;">range</span>(num_steps):</span>
<span id="cb33-90">            unpacked_tensor[unpacked_idx] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">|=</span> uint8tensor[i] <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">&gt;&gt;</span> (bits <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">*</span> j)</span>
<span id="cb33-91">            unpacked_idx <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">+=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span></span>
<span id="cb33-92"></span>
<span id="cb33-93">    unpacked_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">&amp;=</span> mask</span>
<span id="cb33-94">    <span class="cf" style="color: #003B4F;
background-color: null;
font-weight: bold;
font-style: inherit;">return</span> unpacked_tensor</span>
<span id="cb33-95"></span>
<span id="cb33-96">unpacked_tensor <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor([<span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">177</span>, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">255</span>], </span>
<span id="cb33-97">                               dtype<span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span>torch.uint8)</span>
<span id="cb33-98"><span class="co" style="color: #5E5E5E;
background-color: null;
font-style: inherit;"># Answer should be: torch.tensor([1, 0, 3, 2, 3, 3, 3, 3]</span></span>
<span id="cb33-99">unpack_weights(unpacked_tensor, <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">2</span>)</span></code></pre></div></div>
<div class="cell-output cell-output-display" data-execution_count="19">
<pre><code>tensor([1, 0, 3, 2, 3, 3, 3, 3], dtype=torch.uint8)</code></pre>
</div>
</div>
</section>
<section id="beyond-linear-quantization" class="level3">
<h3 class="anchored" data-anchor-id="beyond-linear-quantization">Beyond Linear Quantization</h3>
<ul>
<li><p>Emergent features at scale:- Simply some characteristics or features which appear at scale, when model is large.</p></li>
<li><p>Features predicted by the model meaning the magnitude of the hidden states started to get large thus making the classic quantization schemes quite obsolete, which led to classic linear quantization algorithms just failing on these models.</p></li>
<li><p>Now how to deal with outlier features for LLMs</p></li>
<li><p>Outlier features simply means hidden states with large magnitude.</p></li>
<li><p>So there are some interesting papers such as LLM.int8, SmoothQuant, AWQ.</p>
<ul>
<li>LLM.int8 separates the matmul in two steps:-
<ul>
<li>For non-outliers (smaller values)
<ul>
<li>Perform matmul in int8, then dequantize it.</li>
</ul></li>
<li>For outliers (larger values)
<ul>
<li>Perform matmul in classical way(basically in the dtype of hidden states usually half precision and then you combine these results)</li>
</ul></li>
</ul></li>
<li>SmoothQuant
<ul>
<li>Applies A8W8 scheme(quantize weights and activations)</li>
<li>Given an input it determines some factor and use it to quantize.</li>
<li>migrates the scale variance from activations to weights to reduce the quantization difficulty of activations.</li>
<li>the smoothed activation and the adjusted weight are both easy to quantize.</li>
</ul></li>
<li>AWQ
<ul>
<li>Used a calibration dataset to find out which weights could be responsible of generating outlier features called salient weights.</li>
<li>and then use that information to scale the weights before quantization and also use that scale during inference to rescale the input as well.</li>
</ul></li>
</ul></li>
<li><p>Recent SOTA quantization methods:</p>
<ul>
<li>LL.INT8</li>
<li>GPTQ</li>
<li>SmoothQuant</li>
<li>QLoRA</li>
<li>AWQ</li>
<li>QuIP#</li>
<li>HQQ</li>
<li>AQLM</li>
<li>………..</li>
</ul></li>
<li><p>Challenges of Quantization</p>
<ul>
<li>Retraining (Quantization Aware Training) [less explored]</li>
<li>Limited Hardware support</li>
<li>Calibration dataset needed</li>
<li>packing/unpacking</li>
</ul></li>
<li><p>Some Other resources</p>
<ul>
<li>MIT Han Lab</li>
<li>Huggingface transformers quantization docs/blogposts</li>
<li>llama.cpp discussions</li>
<li>Reddit LocalLlama</li>
</ul></li>
</ul>


</section>

 ]]></description>
  <category>Optimization</category>
  <guid>https://riteshrm.github.io/posts/quantization-in-depth/</guid>
  <pubDate>Fri, 24 May 2024 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/quantization-in-depth/qat-training-precision.png" medium="image" type="image/png" height="81" width="144"/>
</item>
<item>
  <title>Quantization Fundamentals</title>
  <dc:creator>Ritesh Kumar Maurya</dc:creator>
  <link>https://riteshrm.github.io/posts/quantization-fundamentals/</link>
  <description><![CDATA[ 





<ul>
<li><p>This is completely based on <a href="https://learn.deeplearning.ai/courses/quantization-fundamentals/lesson/1/introduction">Quantization Fundamentals</a></p></li>
<li><p>For the code part, you can checkout this <a href="https://github.com/riteshrm/Quantization-Fundamentals-deeplearning.ai-">link</a></p></li>
<li><p><strong>Quantization</strong> helps to reduce the size of the model with little or no degradation.</p></li>
</ul>
<section id="handling-big-models" class="level3">
<h3 class="anchored" data-anchor-id="handling-big-models">Handling Big Models</h3>
<p>Current model compression technique:-</p>
<ol type="1">
<li><p>Pruning:-remove connections that do not improve the model.</p></li>
<li><p>Knowledge Distillation:- Train a smaller model(Student) using the original model(Teacher). Cons:-You need to have enough hardware to fit both teacher as well student both.</p></li>
</ol>
</section>
<section id="options-to-quantize-" class="level3">
<h3 class="anchored" data-anchor-id="options-to-quantize-">Options to quantize:-</h3>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/quantization-fundamentals/S1.png" style="width:80%" class="figure-img">
<figcaption>
Fig.1 - A layer of Neural Network.
</figcaption>
</figure>
<ol type="1">
<li><p>You can quantize weights.</p></li>
<li><p>You can quantize activations that propagate through the layers of neural network</p></li>
</ol>
<p>Idea:Store the parameters of the model in lower precision</p>
</section>
<section id="data-types-and-sizes" class="level3">
<h3 class="anchored" data-anchor-id="data-types-and-sizes">Data Types and Sizes</h3>
<p><strong>Integer</strong></p>
<ol type="1">
<li><p>Unsigned Integer (8-bit):- Range is [0, 255] [0, 2<sup>n</sup>-1] (All 8 bits are used to represent the number)</p></li>
<li><p>Signed Integer (8-bit):- Range is [-128, 127] [-2<sup>n-1</sup>, 2<sup>n-1</sup>-1] (7 bits are used to represent the number and the 8th bit represent the sign 0:Positive 1:Negative)</p></li>
</ol>
<table class="caption-top table">
<thead>
<tr class="header">
<th>Data Type</th>
<th>torch.dtype</th>
<th>torch.dtype alias</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td>8-bit signed integer</td>
<td>torch.int8</td>
<td></td>
</tr>
<tr class="even">
<td>8-bit unsigned integer</td>
<td>torch.uint8</td>
<td></td>
</tr>
<tr class="odd">
<td>16-bit signed integer</td>
<td>torch.int16</td>
<td>torch.short</td>
</tr>
<tr class="even">
<td>32-bit signed integer</td>
<td>torch.int32</td>
<td>torch.int</td>
</tr>
<tr class="odd">
<td>64-bit signed integer</td>
<td>torch.int64</td>
<td>torch.long</td>
</tr>
</tbody>
</table>
<ul>
<li>You can use below mentioned code to find out the more info</li>
</ul>
<div id="657f080f" class="cell" data-execution_count="1">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb1" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb1-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb1-2"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(torch.iinfo(torch.int8))</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<pre><code>iinfo(min=-128, max=127, dtype=int8)</code></pre>
</div>
</div>
<p><strong>Floating Point</strong></p>
<p>3 components in floating point: Sign:- positive/negative (always 1 bit) Exponent(range): impact the representable range of the number Fraction(precision): impact on the precision of the number</p>
<ul>
<li>FP32, BF16, FP16, FP8 are floating point format with a specific number of bits for exponent and the fraction.</li>
</ul>
<ol type="1">
<li>FP32</li>
</ol>
<ul>
<li>Sign: 1 bit</li>
<li>Exponent(range): 8 bit</li>
<li>Fraction(precision): 23 bit</li>
<li>Total: 32 bit</li>
</ul>
<ol start="2" type="1">
<li>BF16</li>
</ol>
<ul>
<li>Sign: 1 bit</li>
<li>Exponent(range): 8 bit</li>
<li>Fraction(precision): 7 bit</li>
<li>Total: 16 bit</li>
</ul>
<ol start="3" type="1">
<li>FP16</li>
</ol>
<ul>
<li>Sign: 1 bit</li>
<li>Exponent(range): 5 bit</li>
<li>Fraction(precision): 10 bit</li>
<li>Total: 16 bit</li>
</ul>
<p><strong>Comparison Of Data Types</strong></p>
<table class="caption-top table">
<thead>
<tr class="header">
<th>Data Type</th>
<th>Precision</th>
<th>Maximum</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td>FP32</td>
<td>Best</td>
<td>~10<sup>+38</sup></td>
</tr>
<tr class="even">
<td>FP16</td>
<td>Better</td>
<td>~10<sup>04</sup></td>
</tr>
<tr class="odd">
<td>BF16</td>
<td>Good</td>
<td>~10<sup>38</sup></td>
</tr>
</tbody>
</table>
<p><br></p>
<table class="caption-top table">
<thead>
<tr class="header">
<th>Data Type</th>
<th>torch.dtype</th>
<th>torch.dtype alias</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td>16-bit floating point</td>
<td>torch.float16</td>
<td>torch.half</td>
</tr>
<tr class="even">
<td>16-bit brain floating point</td>
<td>torch.bfloat16</td>
<td></td>
</tr>
<tr class="odd">
<td>32-bit floating point</td>
<td>torch.float32</td>
<td>torch.float</td>
</tr>
<tr class="even">
<td>64-bit floating point</td>
<td>torch.float64</td>
<td>torch.double</td>
</tr>
</tbody>
</table>
<div id="da27ca13" class="cell" data-execution_count="2">
<div class="code-copy-outer-scaffold"><div class="sourceCode cell-code" id="cb3" style="background: #f1f3f5;"><pre class="sourceCode python code-with-copy"><code class="sourceCode python"><span id="cb3-1"><span class="im" style="color: #00769E;
background-color: null;
font-style: inherit;">import</span> torch</span>
<span id="cb3-2"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">"By default, python stores float data in fp64"</span>)</span>
<span id="cb3-3">value <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> <span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">1</span><span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">/</span><span class="dv" style="color: #AD0000;
background-color: null;
font-style: inherit;">3</span></span>
<span id="cb3-4">tensor_fp64 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor(value, dtype <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.float64)</span>
<span id="cb3-5">tensor_fp32 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor(value, dtype <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.float32)</span>
<span id="cb3-6">tensor_fp16 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor(value, dtype <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.float16)</span>
<span id="cb3-7">tensor_bf16 <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.tensor(value, dtype <span class="op" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">=</span> torch.bfloat16)</span>
<span id="cb3-8"></span>
<span id="cb3-9"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">f"fp64 tensor: </span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">format</span>(tensor_fp64.item(), <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'.60f'</span>)<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>)</span>
<span id="cb3-10"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">f"fp32 tensor: </span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">format</span>(tensor_fp32.item(), <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'.60f'</span>)<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>)</span>
<span id="cb3-11"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">f"fp16 tensor: </span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">format</span>(tensor_fp16.item(), <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'.60f'</span>)<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>)</span>
<span id="cb3-12"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(<span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">f"bf16 tensor: </span><span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">{</span><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">format</span>(tensor_bf16.item(), <span class="st" style="color: #20794D;
background-color: null;
font-style: inherit;">'.60f'</span>)<span class="sc" style="color: #5E5E5E;
background-color: null;
font-style: inherit;">}</span><span class="ss" style="color: #20794D;
background-color: null;
font-style: inherit;">"</span>)</span>
<span id="cb3-13"></span>
<span id="cb3-14"><span class="bu" style="color: null;
background-color: null;
font-style: inherit;">print</span>(torch.finfo(torch.bfloat16))</span></code></pre></div></div>
<div class="cell-output cell-output-stdout">
<pre><code>By default, python stores float data in fp64
fp64 tensor: 0.333333333333333314829616256247390992939472198486328125000000
fp32 tensor: 0.333333343267440795898437500000000000000000000000000000000000
fp16 tensor: 0.333251953125000000000000000000000000000000000000000000000000
bf16 tensor: 0.333984375000000000000000000000000000000000000000000000000000
finfo(resolution=0.01, min=-3.38953e+38, max=3.38953e+38, eps=0.0078125, smallest_normal=1.17549e-38, tiny=1.17549e-38, dtype=bfloat16)</code></pre>
</div>
</div>
<p><strong>PyTorch Downcasting</strong></p>
<ul>
<li><p>when a higher data type converted to a lower data type, it results in loss of data</p></li>
<li><p>Advantages:</p>
<ul>
<li>Reduced memory footprint</li>
<li>Increased compute and speed (Depends on the hardware)</li>
</ul></li>
<li><p>Disadvantages:</p>
<ul>
<li>Less precise</li>
</ul></li>
<li><p>Use case:</p>
<ul>
<li>Mixed precision training
<ul>
<li>Do computation in smaller precision (FP16/BF16/FP8)</li>
<li>Store and update the weights in higher precision (FP32)</li>
</ul></li>
</ul></li>
</ul>
</section>
<section id="loading-models-by-data-type" class="level3">
<h3 class="anchored" data-anchor-id="loading-models-by-data-type">Loading Models by data type</h3>
<ul>
<li><p>target_dtype = torch.float16 or torch.bfloat16</p></li>
<li><p>model = model.to(target_dtype)</p></li>
<li><p>model = model.half() for fp16</p></li>
<li><p>model = model.bfloat16() for bfloat16</p></li>
<li><p>Always use bfloat16 instead of float16 while using pytorch-cpu</p></li>
<li><p>FP32 is default in pytorch</p></li>
<li><p>model.get_memory_footprint()/1e+6</p></li>
<li><p>torch.set_default_dtype(desired_dtype) # By doing so we can directly load the model in desired dtype without loading in full precision and then quantizing it</p></li>
<li><p>set it back to float32 to avoid unnecessary behaviors</p></li>
</ul>
</section>
<section id="quantization-theory" class="level3">
<h3 class="anchored" data-anchor-id="quantization-theory">Quantization Theory</h3>
<ul>
<li><p>Quantization refers to the process of mapping a large set to a smaller set of values.</p></li>
<li><p>How do we convert the FP32 weights to INT8 without losing too much information??</p>
<ul>
<li>It is done using a linear mapping using linear mapping parameters.</li>
<li>s = scale</li>
<li>z = zero point</li>
</ul></li>
<li><p>How do we get back our original tensor from the quantized tensor?</p>
<ul>
<li>We can’t get exactly the original tensor but using dequantization following linear relationship that used to quantize the original tensor.</li>
</ul></li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/quantization-fundamentals/Q1.png" style="width:50%" class="figure-img">
<figcaption>
Fig.2 - Comparison of tensors.
</figcaption>
</figure>
<p><strong>Quantize Using Quanto Library</strong></p>
<ul>
<li>from quanto import quantize, freeze</li>
<li>quantize(model, weights = desired_dtype, activations = desired_dtype)</li>
<li>freeze(model)</li>
<li>quantize create an intermediate state of the model</li>
<li>after calling freeze, we get the quantized weights</li>
</ul>
<p><strong>Uses of the Intermediate State</strong></p>
<ul>
<li>Calibration
<ul>
<li>Calibrate model when quantizing the activations of the model.
<ul>
<li>Range of activation values depends on what input was given. (e.g.&nbsp;different input text will generate different activations)</li>
<li>Min/Max of activation ranges are used to perform linear quantization.</li>
<li>How to get min and max range of activations?
<ul>
<li>Gather sample input data.</li>
<li>Run inference.</li>
<li>Calculate min/max of activations</li>
</ul></li>
</ul></li>
<li>Result: better quantized activations</li>
</ul></li>
<li>Quantization Aware Training
<ul>
<li>Training in a way that controls how the model performs once it is quantized.</li>
<li>Intermediate state holds both(quantized as well as unquantized weights).</li>
<li>Use quantized version of model in forward pass (e.g.&nbsp;BF16)</li>
<li>Update original, unquantized version of model weights during back propagation (e.g.&nbsp;FP32)</li>
</ul></li>
<li>In L4 there is a function in helper.py to calculate the model size</li>
</ul>
<p><strong>Linear Quantization</strong></p>
<p>Even if it looks very simple, it is used in many SOTA quantization methods:</p>
<ul>
<li>AWQ: Activation-aware Weight Quantization</li>
<li>GPTQ: GPT Quantized</li>
<li>BNB: BitsandBytes Quantization</li>
</ul>
<figure style="text-align: center;" class="figure">
<img src="https://riteshrm.github.io/posts/quantization-fundamentals/Q2.png" style="width:50%" class="figure-img">
<figcaption>
Fig.3 - Range
</figcaption>
</figure>
<ul>
<li>Simple idea: linear mapping</li>
<li>r = s(q-z)
<ul>
<li>where</li>
<li>r:- original value(e.g.&nbsp;in FP32)</li>
<li>s:- scale(e.g.&nbsp;in FP32)</li>
<li>q:- quantized value(e.g.&nbsp;in INT8)</li>
<li>z:- zero point(e.g.&nbsp;INT8)</li>
</ul></li>
<li>How do we get scale and zero point??
<ul>
<li>s = (r_max-r_min)/(q_max-q_min)</li>
<li>z = int(round(q_min-r_min/s))</li>
</ul></li>
</ul>
</section>
<section id="quantization-of-llms" class="level3">
<h3 class="anchored" data-anchor-id="quantization-of-llms">Quantization of LLMs</h3>
<p>Recent SOTA quantization methods:-</p>
<ul>
<li>LLM.INT8 (only 8-bit)
<ul>
<li>Decomposes the mat-mul in two stages (outlier part in float16 and non-outlier part in int8).</li>
</ul></li>
<li>QLoRA (only 4-bit)
<ul>
<li>Quantize as well as fine-tune the adapters</li>
</ul></li>
<li>AWQ</li>
<li>GPTQ</li>
<li>SmoothQuant</li>
</ul>
<p>More recent SOTA quantization methods for 2-bit quantization</p>
<ul>
<li>QuIP#</li>
<li>HQQ</li>
<li>AQLM</li>
</ul>
<p>All are <strong>open-source</strong></p>
<p>Some Quantization Methods require calibration (from above)</p>
<p>Some Quantization Methods require Adjustments</p>
<p>Many of these methods were applied to LLMs, but if we want then we can apply to other type of models by making few adjustments to the quantization methods</p>
<ul>
<li><p>Some methods can be applied without making adjustments</p>
<ul>
<li>Linear quantization</li>
<li>LL.INT8</li>
<li>QLoRA</li>
<li>HQQ</li>
</ul></li>
<li><p>Other approaches are data-dependent</p></li>
<li><p>There are distributors on HuggingFacewhich gives a quantized version of popular models (TheBloke)</p></li>
<li><p>Checkout HuggingFace Open <strong>LLM leaderboard</strong> to see how these quantized models are performing</p></li>
<li><p>Benefits of fine-tuning a quantized model:</p>
<ul>
<li>Recover the accuracy from quantization</li>
<li>Tailor your model for specific use-cases and applications</li>
</ul></li>
<li><p>Fine tune with Quantization Aware Training (QAT)</p>
<ul>
<li>Not compatible with Post Training Quantization (PTQ) techniques.</li>
<li>The linear quantization method is an example of PTQ.</li>
<li><a href="https://pytorch.org/blog/finetune-llms/">PEFT + QLoRA</a>
<ul>
<li>QLoRa quantizes the pre-trained base weights in 4-bit precision.</li>
<li>This matches the precision of the LoRA weights.</li>
<li>This allows the model to add the activations of the pre-trained and adapter weights.</li>
<li>This sum of the two activations can be fed as the input to the next layer of the network.</li>
</ul></li>
</ul></li>
</ul>


</section>

 ]]></description>
  <category>Optimization</category>
  <guid>https://riteshrm.github.io/posts/quantization-fundamentals/</guid>
  <pubDate>Mon, 13 May 2024 00:00:00 GMT</pubDate>
  <media:content url="https://riteshrm.github.io/posts/quantization-fundamentals/qat-training-precision.png" medium="image" type="image/png" height="81" width="144"/>
</item>
</channel>
</rss>
