{
  "id": 689386,
  "title": "1st Place Solution — Five-Model Ensemble with Length-Adaptive Allocation",
  "url": "/competitions/stanford-rna-3d-folding-2/discussion/689386",
  "author_name": "k2011yi",
  "post_date": "2026-04-08T14:32:11.065000",
  "votes": 25,
  "comment_count": 7,
  "views": 0,
  "content": "<h2>Acknowledgements</h2>\n<p>We are team_cp ( <a href=\"https://www.kaggle.com/naganohikaru\" target=\"_blank\">@naganohikaru</a>, <a href=\"https://www.kaggle.com/yutaroito\" target=\"_blank\">@yutaroito</a>), a two-person team.<br>\nThis is our second time participating in the Stanford RNA 3D Folding series; we placed 25th in Part 1.<br>\nThe experience from Part 1 — particularly understanding which model combinations held up on unseen data and learning the power of template-based modeling — gave us a strong foundation for this competition.  </p>\n<p>We are deeply grateful to the competition organizers, Stanford University, and the many Kagglers who shared public notebooks and insights throughout the competition!</p>\n<hr>\n<h2>Summary</h2>\n<p>Our solution combines five independent structure prediction models into a single 5-prediction submission, with each model's allocation driven by sequence length.<br>\nSince scoring is best-of-5, the goal is to maximize structural diversity across the five predictions.   </p>\n<h3>The five models are:</h3>\n<table>\n<thead>\n<tr>\n<th>Model</th>\n<th>Role</th>\n</tr>\n</thead>\n<tbody>\n<tr>\n<td><strong>TBM</strong> (Template-Based Modeling)</td>\n<td>Primary predictor for seq_len ≥ 250; fallback for all lengths</td>\n</tr>\n<tr>\n<td><strong>Boltz2</strong></td>\n<td>Primary predictor for seq_len &lt; 250; secondary for 250–999</td>\n</tr>\n<tr>\n<td><strong>RNAPro</strong></td>\n<td>Diffusion-based refinement for seq_len &lt; 1000</td>\n</tr>\n<tr>\n<td><strong>DRFold2</strong></td>\n<td>RNA-specific deep learning for short sequences</td>\n</tr>\n<tr>\n<td><strong>Protenix</strong></td>\n<td>AlphaFold3-based; short sequences and ≥ 1000 nt</td>\n</tr>\n</tbody>\n</table>\n<h3>Final ensemble composition (5 predictions per target):</h3>\n<table>\n<thead>\n<tr>\n<th>seq_len</th>\n<th>Pred 1</th>\n<th>Pred 2</th>\n<th>Pred 3</th>\n<th>Pred 4</th>\n<th>Pred 5</th>\n</tr>\n</thead>\n<tbody>\n<tr>\n<td>&lt; 250</td>\n<td>Boltz2₁</td>\n<td>Boltz2₂</td>\n<td>RNApro₁</td>\n<td>Protenix₁</td>\n<td>DRFold2₁</td>\n</tr>\n<tr>\n<td>250 – 999</td>\n<td>TBM₁</td>\n<td>Boltz2₁</td>\n<td>RNApro₁</td>\n<td>RNApro₂</td>\n<td>Boltz2₂</td>\n</tr>\n<tr>\n<td>≥ 1000</td>\n<td>TBM₁</td>\n<td>TBM₂</td>\n<td>TBM₃</td>\n<td>Protenix₁</td>\n<td>Protenix₂</td>\n</tr>\n</tbody>\n</table>\n<p>RNApro and Boltz2 skip sequences ≥ 1000 nt (OOM risk), so the ≥ 1000 nt tier uses TBM for 3 predictions and Protenix for the remaining 2.</p>\n<h3>Final scores (selected submission):</h3>\n<table>\n<thead>\n<tr>\n<th>Comp. Public LB</th>\n<th>Comp. Private LB</th>\n<th>Final Public LB</th>\n<th>Final Private LB</th>\n</tr>\n</thead>\n<tbody>\n<tr>\n<td>0.43837</td>\n<td>0.60037</td>\n<td>0.42854</td>\n<td><strong>0.49669</strong></td>\n</tr>\n</tbody>\n</table>\n<hr>\n<h2>Phase 1: Template-Based Modeling (TBM)</h2>\n<p>TBM is the backbone of our pipeline for medium and long sequences.<br>\nWe search a combined train + validation pool using BioPython's <code>PairwiseAligner</code> (global mode), filtering to templates whose length is within 30% of the query length. Alignments are scored and normalized; the top-30 templates form the candidate pool.</p>\n<p><strong>Diversity within TBM predictions:</strong></p>\n<ul>\n<li>Prediction 1: top-scoring template, used as-is.</li>\n<li>Predictions 2–5 (when TBM fills multiple slots): sampled from the top-12 with exponential weighting. Already-used templates receive a 0.1× weight penalty to discourage duplication.</li>\n</ul>\n<p><strong>Gap filling:</strong></p>\n<ul>\n<li>Aligned gaps are filled by linear interpolation between the two nearest valid C1' coordinates.</li>\n<li>One-sided gaps (at chain termini) are extended by 5.95 Å steps along the extrapolated direction.</li>\n<li>If no template exists at all, a fallback linear structure is placed along the X-axis at 5.95 Å steps.</li>\n</ul>\n<p><strong>Post-processing (<code>adaptive_rna_constraints</code>):</strong>\nEach TBM prediction is refined per-chain with:</p>\n<ol>\n<li>Bond length correction: i→i+1 distance → 5.95 Å</li>\n<li>Angle correction: i→i+2 distance → 10.2 Å</li>\n<li>Laplacian smoothing to remove kinks</li>\n<li>Steric self-avoidance (3.2 Å threshold) for chains of length ≥ 25</li>\n</ol>\n<p>The correction strength scales with <code>(1 − template_similarity)</code> so that near-identical templates are barely modified while low-similarity matches are corrected more aggressively.</p>\n<hr>\n<h2>Phase 2: DRFold2</h2>\n<p>DRFold2 (cfg97 configuration, 20 models) provides an RNA-specific deep-learning signal, contributing 1 prediction for sequences shorter than 250 nt.<br>\nFrom Part 1, we confirmed that cfg97 outperformed other DRFold2 configurations.</p>\n<p>Within that range, the number of models run scales with sequence length:</p>\n<ul>\n<li>L &gt; 200 nt: 5 models <code>[13, 6, 14, 5, 3]</code></li>\n<li>L &gt; 100 nt: 10 models <code>[13, 6, 14, 12, 7, 2, 5, 19, 10, 9]</code></li>\n<li>L ≤ 100 nt: all 20 models</li>\n</ul>\n<p>For each model's output, we compute an energy score (bond lengths, bond angles, stacking) and normalize by the median absolute deviation across predictions. The top-5 scoring structures are selected.</p>\n<hr>\n<h2>Phase 3: RNAPro</h2>\n<p>RNAPro (NVIDIA's Part 1 winner) is used for all sequences under 1000 nt.<br>\nIt contributes 2 predictions for mid-range sequences (250–999 nt) and 1 prediction for short sequences (&lt; 250 nt), each conditioned on a different TBM template (top-1 and top-2).</p>\n<p>Configuration:</p>\n<ul>\n<li>MSA enabled (<code>--use_msa true</code>)</li>\n<li>Pre-computed TBM templates (<code>--use_template ca_precomputed</code>)</li>\n<li>RibonanzaNet2 embeddings</li>\n<li>N_STEP = 200, N_CYCLE = 10, N_SAMPLE = 1</li>\n</ul>\n<hr>\n<h2>Phase 4: Boltz2</h2>\n<p>Boltz2 is the primary model for short sequences (&lt; 250 nt), contributing 2 predictions, and contributes 2 predictions for mid-range sequences (250–999 nt) as well.<br>\nIt is skipped for sequences ≥ 1000 nt to avoid OOM.</p>\n<ul>\n<li><code>diffusion_samples = 10</code> structures generated per target</li>\n<li>Top-5 selected by combined plddt + confidence score</li>\n<li>Ligand information (SMILES) included in YAML input</li>\n<li>Multi-chain targets: only RNA chains are folded (<code>use_all_chains = False</code>) to avoid OOM with large complexes</li>\n</ul>\n<hr>\n<h2>Phase 5: Protenix</h2>\n<p>Protenix (ByteDance, AlphaFold3 architecture) contributes 1 prediction for short sequences (&lt; 250 nt) and 2 predictions for very long sequences (≥ 1000 nt).</p>\n<ul>\n<li>RNA MSA enabled (<code>USE_RNA_MSA = true</code>)</li>\n</ul>\n<p><strong>Long-sequence handling (≥ 1000 nt):</strong></p>\n<p>Protenix has a practical per-inference memory limit, so sequences longer than <code>MAX_SEQ_LEN = 512</code> nt are processed with a sliding-window chunking strategy:</p>\n<ol>\n<li><p><strong>Chunking</strong> — <code>split_sequence(seq, max_len=512, overlap=128)</code> divides the full sequence into overlapping windows.\nThe step size is <code>512 − 128 = 384</code> nt, so a 1000 nt sequence produces three chunks: <code>[0:512]</code>, <code>[384:896]</code>, <code>[768:1000]</code>.</p></li>\n<li><p><strong>Per-chunk inference</strong> — each chunk is fed to Protenix independently as a separate short-sequence target (its own JSON input and <code>InferenceDataset</code>).\n<code>update_inference_configs</code> is called with the chunk token count so internal model buffers are sized correctly.</p></li>\n<li><p><strong>C1' extraction</strong> — from each chunk's raw atom-level output, C1' atoms are identified by matching <code>res_id</code> (1-indexed within the chunk) and <code>atom_name == \"C1'\"</code>.\nA two-stage fallback is used: first <code>centre_atom_mask</code>, then <code>atom_to_tokatom_idx == 12</code>.</p></li>\n<li><p><strong>Assembly</strong> — extracted C1' coordinates <code>(N_sample, chunk_len, 3)</code> are written into a pre-allocated <code>full_coords (N_sample, seq_len, 3)</code> array at <code>[:, start:end, :]</code>.\nOverlapping positions are overwritten by the later (right-side) chunk.</p></li>\n<li><p><strong>Memory cleanup</strong> — <code>torch.cuda.empty_cache()</code> and <code>gc.collect()</code> are called after every chunk to avoid GPU OOM on very long targets.</p></li>\n</ol>\n<hr>\n<h2>What Worked</h2>\n<h3>The combination of five structurally diverse models.</h3>\n<p>From Part 1 we confirmed that ensembling Boltz, Protenix, and DRFold2 was robustly better on unseen sequences than any single model alone.<br>\nBuilding on that, Part 2 added RNAPro (the Part 1 winner) as a powerful refinement step, which significantly improved our mid-range sequences.</p>\n<h3>TBM as the strong backbone for medium and long sequences.</h3>\n<p>TBM proved highly competitive whenever a similar sequence existed in the training data.<br>\nFor sequences ≥ 250 nt, allocating multiple predictions to TBM and using other models to cover the remaining predictions was consistently better than the reverse.</p>\n<h3>Length-adaptive allocation.</h3>\n<p>Rather than a one-size-fits-all ensemble, we tuned how many predictions each model contributes based on empirical performance at each length range.<br>\nThe \"overlay\" structure of the pipeline (models are run in order and later models overwrite earlier ones) made this easy to tune incrementally.<br>\nThe 250 nt boundary was selected by balancing inference time against score: models like Boltz2 and DRFold2 are fast enough for short sequences within the time limit but become impractical beyond this point, while TBM scales well to longer sequences at low cost.</p>\n<h3>Diversity over TBM dependency.</h3>\n<p>We treated TBM as a backbone only where it is clearly strongest (longer sequences with close training-set matches), and filled the remaining predictions with diverse models.<br>\nFor short sequences (&lt; 250 nt), we deliberately avoided TBM as the primary predictor and instead relied on Boltz2, DRFold2, and Protenix — models that make predictions purely from sequence without template dependency.<br>\nFor the remaining slots outside of short sequences, we combined RNAPro — which starts from a TBM template but refines it into an independently generated structure — with template-free models (Boltz2 and Protenix), ensuring diversity across all five predictions.<br>\nWe believe this diversity contributed to our performance on the private leaderboard, which contained harder targets where no close template existed.</p>\n<hr>\n<h2>Authors</h2>\n<p>team_cp: <a href=\"https://www.kaggle.com/naganohikaru\" target=\"_blank\">@naganohikaru</a>, <a href=\"https://www.kaggle.com/yutaroito\" target=\"_blank\">@yutaroito</a></p>\n<hr>\n<h2>References</h2>\n<ul>\n<li><a href=\"https://www.kaggle.com/competitions/stanford-rna-3d-folding/writeups/25th-place-solution\" target=\"_blank\">Our Part 1 solution (25th place)</a> — baseline ensemble strategy and lessons learned carried into Part 2.</li>\n<li><a href=\"https://www.kaggle.com/competitions/stanford-rna-3d-folding-2/discussion/668412\" target=\"_blank\">Part 2 solution discussion</a> — competition discussion thread for this solution.</li>\n<li><a href=\"https://www.kaggle.com/code/qiweiyin/protenix-v1-inference-2026\" target=\"_blank\">Protenix v1 inference notebook</a> — public notebook that formed the basis of our Protenix integration.</li>\n<li><a href=\"https://www.kaggle.com/code/qamarmath/beginner-to-advanced-rna-3d-structure-predicti\" target=\"_blank\">Beginner-to-advanced RNA 3D structure prediction</a> — general pipeline reference used during development.</li>\n</ul>",
  "messages": [
    {
      "id": 3438018,
      "postDate": "2026-04-08T14:32:11.067Z",
      "content": "<h2>Acknowledgements</h2>\n<p>We are team_cp ( <a href=\"https://www.kaggle.com/naganohikaru\" target=\"_blank\">@naganohikaru</a>, <a href=\"https://www.kaggle.com/yutaroito\" target=\"_blank\">@yutaroito</a>), a two-person team.<br>\nThis is our second time participating in the Stanford RNA 3D Folding series; we placed 25th in Part 1.<br>\nThe experience from Part 1 — particularly understanding which model combinations held up on unseen data and learning the power of template-based modeling — gave us a strong foundation for this competition.  </p>\n<p>We are deeply grateful to the competition organizers, Stanford University, and the many Kagglers who shared public notebooks and insights throughout the competition!</p>\n<hr>\n<h2>Summary</h2>\n<p>Our solution combines five independent structure prediction models into a single 5-prediction submission, with each model's allocation driven by sequence length.<br>\nSince scoring is best-of-5, the goal is to maximize structural diversity across the five predictions.   </p>\n<h3>The five models are:</h3>\n<table>\n<thead>\n<tr>\n<th>Model</th>\n<th>Role</th>\n</tr>\n</thead>\n<tbody>\n<tr>\n<td><strong>TBM</strong> (Template-Based Modeling)</td>\n<td>Primary predictor for seq_len ≥ 250; fallback for all lengths</td>\n</tr>\n<tr>\n<td><strong>Boltz2</strong></td>\n<td>Primary predictor for seq_len &lt; 250; secondary for 250–999</td>\n</tr>\n<tr>\n<td><strong>RNAPro</strong></td>\n<td>Diffusion-based refinement for seq_len &lt; 1000</td>\n</tr>\n<tr>\n<td><strong>DRFold2</strong></td>\n<td>RNA-specific deep learning for short sequences</td>\n</tr>\n<tr>\n<td><strong>Protenix</strong></td>\n<td>AlphaFold3-based; short sequences and ≥ 1000 nt</td>\n</tr>\n</tbody>\n</table>\n<h3>Final ensemble composition (5 predictions per target):</h3>\n<table>\n<thead>\n<tr>\n<th>seq_len</th>\n<th>Pred 1</th>\n<th>Pred 2</th>\n<th>Pred 3</th>\n<th>Pred 4</th>\n<th>Pred 5</th>\n</tr>\n</thead>\n<tbody>\n<tr>\n<td>&lt; 250</td>\n<td>Boltz2₁</td>\n<td>Boltz2₂</td>\n<td>RNApro₁</td>\n<td>Protenix₁</td>\n<td>DRFold2₁</td>\n</tr>\n<tr>\n<td>250 – 999</td>\n<td>TBM₁</td>\n<td>Boltz2₁</td>\n<td>RNApro₁</td>\n<td>RNApro₂</td>\n<td>Boltz2₂</td>\n</tr>\n<tr>\n<td>≥ 1000</td>\n<td>TBM₁</td>\n<td>TBM₂</td>\n<td>TBM₃</td>\n<td>Protenix₁</td>\n<td>Protenix₂</td>\n</tr>\n</tbody>\n</table>\n<p>RNApro and Boltz2 skip sequences ≥ 1000 nt (OOM risk), so the ≥ 1000 nt tier uses TBM for 3 predictions and Protenix for the remaining 2.</p>\n<h3>Final scores (selected submission):</h3>\n<table>\n<thead>\n<tr>\n<th>Comp. Public LB</th>\n<th>Comp. Private LB</th>\n<th>Final Public LB</th>\n<th>Final Private LB</th>\n</tr>\n</thead>\n<tbody>\n<tr>\n<td>0.43837</td>\n<td>0.60037</td>\n<td>0.42854</td>\n<td><strong>0.49669</strong></td>\n</tr>\n</tbody>\n</table>\n<hr>\n<h2>Phase 1: Template-Based Modeling (TBM)</h2>\n<p>TBM is the backbone of our pipeline for medium and long sequences.<br>\nWe search a combined train + validation pool using BioPython's <code>PairwiseAligner</code> (global mode), filtering to templates whose length is within 30% of the query length. Alignments are scored and normalized; the top-30 templates form the candidate pool.</p>\n<p><strong>Diversity within TBM predictions:</strong></p>\n<ul>\n<li>Prediction 1: top-scoring template, used as-is.</li>\n<li>Predictions 2–5 (when TBM fills multiple slots): sampled from the top-12 with exponential weighting. Already-used templates receive a 0.1× weight penalty to discourage duplication.</li>\n</ul>\n<p><strong>Gap filling:</strong></p>\n<ul>\n<li>Aligned gaps are filled by linear interpolation between the two nearest valid C1' coordinates.</li>\n<li>One-sided gaps (at chain termini) are extended by 5.95 Å steps along the extrapolated direction.</li>\n<li>If no template exists at all, a fallback linear structure is placed along the X-axis at 5.95 Å steps.</li>\n</ul>\n<p><strong>Post-processing (<code>adaptive_rna_constraints</code>):</strong>\nEach TBM prediction is refined per-chain with:</p>\n<ol>\n<li>Bond length correction: i→i+1 distance → 5.95 Å</li>\n<li>Angle correction: i→i+2 distance → 10.2 Å</li>\n<li>Laplacian smoothing to remove kinks</li>\n<li>Steric self-avoidance (3.2 Å threshold) for chains of length ≥ 25</li>\n</ol>\n<p>The correction strength scales with <code>(1 − template_similarity)</code> so that near-identical templates are barely modified while low-similarity matches are corrected more aggressively.</p>\n<hr>\n<h2>Phase 2: DRFold2</h2>\n<p>DRFold2 (cfg97 configuration, 20 models) provides an RNA-specific deep-learning signal, contributing 1 prediction for sequences shorter than 250 nt.<br>\nFrom Part 1, we confirmed that cfg97 outperformed other DRFold2 configurations.</p>\n<p>Within that range, the number of models run scales with sequence length:</p>\n<ul>\n<li>L &gt; 200 nt: 5 models <code>[13, 6, 14, 5, 3]</code></li>\n<li>L &gt; 100 nt: 10 models <code>[13, 6, 14, 12, 7, 2, 5, 19, 10, 9]</code></li>\n<li>L ≤ 100 nt: all 20 models</li>\n</ul>\n<p>For each model's output, we compute an energy score (bond lengths, bond angles, stacking) and normalize by the median absolute deviation across predictions. The top-5 scoring structures are selected.</p>\n<hr>\n<h2>Phase 3: RNAPro</h2>\n<p>RNAPro (NVIDIA's Part 1 winner) is used for all sequences under 1000 nt.<br>\nIt contributes 2 predictions for mid-range sequences (250–999 nt) and 1 prediction for short sequences (&lt; 250 nt), each conditioned on a different TBM template (top-1 and top-2).</p>\n<p>Configuration:</p>\n<ul>\n<li>MSA enabled (<code>--use_msa true</code>)</li>\n<li>Pre-computed TBM templates (<code>--use_template ca_precomputed</code>)</li>\n<li>RibonanzaNet2 embeddings</li>\n<li>N_STEP = 200, N_CYCLE = 10, N_SAMPLE = 1</li>\n</ul>\n<hr>\n<h2>Phase 4: Boltz2</h2>\n<p>Boltz2 is the primary model for short sequences (&lt; 250 nt), contributing 2 predictions, and contributes 2 predictions for mid-range sequences (250–999 nt) as well.<br>\nIt is skipped for sequences ≥ 1000 nt to avoid OOM.</p>\n<ul>\n<li><code>diffusion_samples = 10</code> structures generated per target</li>\n<li>Top-5 selected by combined plddt + confidence score</li>\n<li>Ligand information (SMILES) included in YAML input</li>\n<li>Multi-chain targets: only RNA chains are folded (<code>use_all_chains = False</code>) to avoid OOM with large complexes</li>\n</ul>\n<hr>\n<h2>Phase 5: Protenix</h2>\n<p>Protenix (ByteDance, AlphaFold3 architecture) contributes 1 prediction for short sequences (&lt; 250 nt) and 2 predictions for very long sequences (≥ 1000 nt).</p>\n<ul>\n<li>RNA MSA enabled (<code>USE_RNA_MSA = true</code>)</li>\n</ul>\n<p><strong>Long-sequence handling (≥ 1000 nt):</strong></p>\n<p>Protenix has a practical per-inference memory limit, so sequences longer than <code>MAX_SEQ_LEN = 512</code> nt are processed with a sliding-window chunking strategy:</p>\n<ol>\n<li><p><strong>Chunking</strong> — <code>split_sequence(seq, max_len=512, overlap=128)</code> divides the full sequence into overlapping windows.\nThe step size is <code>512 − 128 = 384</code> nt, so a 1000 nt sequence produces three chunks: <code>[0:512]</code>, <code>[384:896]</code>, <code>[768:1000]</code>.</p></li>\n<li><p><strong>Per-chunk inference</strong> — each chunk is fed to Protenix independently as a separate short-sequence target (its own JSON input and <code>InferenceDataset</code>).\n<code>update_inference_configs</code> is called with the chunk token count so internal model buffers are sized correctly.</p></li>\n<li><p><strong>C1' extraction</strong> — from each chunk's raw atom-level output, C1' atoms are identified by matching <code>res_id</code> (1-indexed within the chunk) and <code>atom_name == \"C1'\"</code>.\nA two-stage fallback is used: first <code>centre_atom_mask</code>, then <code>atom_to_tokatom_idx == 12</code>.</p></li>\n<li><p><strong>Assembly</strong> — extracted C1' coordinates <code>(N_sample, chunk_len, 3)</code> are written into a pre-allocated <code>full_coords (N_sample, seq_len, 3)</code> array at <code>[:, start:end, :]</code>.\nOverlapping positions are overwritten by the later (right-side) chunk.</p></li>\n<li><p><strong>Memory cleanup</strong> — <code>torch.cuda.empty_cache()</code> and <code>gc.collect()</code> are called after every chunk to avoid GPU OOM on very long targets.</p></li>\n</ol>\n<hr>\n<h2>What Worked</h2>\n<h3>The combination of five structurally diverse models.</h3>\n<p>From Part 1 we confirmed that ensembling Boltz, Protenix, and DRFold2 was robustly better on unseen sequences than any single model alone.<br>\nBuilding on that, Part 2 added RNAPro (the Part 1 winner) as a powerful refinement step, which significantly improved our mid-range sequences.</p>\n<h3>TBM as the strong backbone for medium and long sequences.</h3>\n<p>TBM proved highly competitive whenever a similar sequence existed in the training data.<br>\nFor sequences ≥ 250 nt, allocating multiple predictions to TBM and using other models to cover the remaining predictions was consistently better than the reverse.</p>\n<h3>Length-adaptive allocation.</h3>\n<p>Rather than a one-size-fits-all ensemble, we tuned how many predictions each model contributes based on empirical performance at each length range.<br>\nThe \"overlay\" structure of the pipeline (models are run in order and later models overwrite earlier ones) made this easy to tune incrementally.<br>\nThe 250 nt boundary was selected by balancing inference time against score: models like Boltz2 and DRFold2 are fast enough for short sequences within the time limit but become impractical beyond this point, while TBM scales well to longer sequences at low cost.</p>\n<h3>Diversity over TBM dependency.</h3>\n<p>We treated TBM as a backbone only where it is clearly strongest (longer sequences with close training-set matches), and filled the remaining predictions with diverse models.<br>\nFor short sequences (&lt; 250 nt), we deliberately avoided TBM as the primary predictor and instead relied on Boltz2, DRFold2, and Protenix — models that make predictions purely from sequence without template dependency.<br>\nFor the remaining slots outside of short sequences, we combined RNAPro — which starts from a TBM template but refines it into an independently generated structure — with template-free models (Boltz2 and Protenix), ensuring diversity across all five predictions.<br>\nWe believe this diversity contributed to our performance on the private leaderboard, which contained harder targets where no close template existed.</p>\n<hr>\n<h2>Authors</h2>\n<p>team_cp: <a href=\"https://www.kaggle.com/naganohikaru\" target=\"_blank\">@naganohikaru</a>, <a href=\"https://www.kaggle.com/yutaroito\" target=\"_blank\">@yutaroito</a></p>\n<hr>\n<h2>References</h2>\n<ul>\n<li><a href=\"https://www.kaggle.com/competitions/stanford-rna-3d-folding/writeups/25th-place-solution\" target=\"_blank\">Our Part 1 solution (25th place)</a> — baseline ensemble strategy and lessons learned carried into Part 2.</li>\n<li><a href=\"https://www.kaggle.com/competitions/stanford-rna-3d-folding-2/discussion/668412\" target=\"_blank\">Part 2 solution discussion</a> — competition discussion thread for this solution.</li>\n<li><a href=\"https://www.kaggle.com/code/qiweiyin/protenix-v1-inference-2026\" target=\"_blank\">Protenix v1 inference notebook</a> — public notebook that formed the basis of our Protenix integration.</li>\n<li><a href=\"https://www.kaggle.com/code/qamarmath/beginner-to-advanced-rna-3d-structure-predicti\" target=\"_blank\">Beginner-to-advanced RNA 3D structure prediction</a> — general pipeline reference used during development.</li>\n</ul>",
      "rawMarkdown": "## Acknowledgements\n\nWe are team_cp ( @naganohikaru, @yutaroito), a two-person team.  \nThis is our second time participating in the Stanford RNA 3D Folding series; we placed 25th in Part 1.  \nThe experience from Part 1 — particularly understanding which model combinations held up on unseen data and learning the power of template-based modeling — gave us a strong foundation for this competition.  \n  \nWe are deeply grateful to the competition organizers, Stanford University, and the many Kagglers who shared public notebooks and insights throughout the competition!\n\n---\n\n## Summary\n\nOur solution combines five independent structure prediction models into a single 5-prediction submission, with each model's allocation driven by sequence length.  \nSince scoring is best-of-5, the goal is to maximize structural diversity across the five predictions.   \n### The five models are:\n\n| Model | Role |\n|---|---|\n| **TBM** (Template-Based Modeling) | Primary predictor for seq_len ≥ 250; fallback for all lengths |\n| **Boltz2** | Primary predictor for seq_len < 250; secondary for 250–999 |\n| **RNAPro** | Diffusion-based refinement for seq_len < 1000 |\n| **DRFold2** | RNA-specific deep learning for short sequences |\n| **Protenix** | AlphaFold3-based; short sequences and ≥ 1000 nt |\n  \n  \n### Final ensemble composition (5 predictions per target):\n| seq_len | Pred 1 | Pred 2 | Pred 3 | Pred 4 | Pred 5 |\n|---|---|---|---|---|---|\n| < 250 | Boltz2₁ | Boltz2₂ | RNApro₁ | Protenix₁ | DRFold2₁ |\n| 250 – 999 | TBM₁ | Boltz2₁ | RNApro₁ | RNApro₂ | Boltz2₂ |\n| ≥ 1000 | TBM₁ | TBM₂ | TBM₃ | Protenix₁ | Protenix₂ |\n\nRNApro and Boltz2 skip sequences ≥ 1000 nt (OOM risk), so the ≥ 1000 nt tier uses TBM for 3 predictions and Protenix for the remaining 2.\n\n### Final scores (selected submission):\n\n| Comp. Public LB | Comp. Private LB | Final Public LB | Final Private LB |\n|---|---|---|---|\n| 0.43837 | 0.60037 | 0.42854 | **0.49669** |\n\n---\n\n## Phase 1: Template-Based Modeling (TBM)\n\nTBM is the backbone of our pipeline for medium and long sequences.  \nWe search a combined train + validation pool using BioPython's `PairwiseAligner` (global mode), filtering to templates whose length is within 30% of the query length. Alignments are scored and normalized; the top-30 templates form the candidate pool.\n\n**Diversity within TBM predictions:**\n- Prediction 1: top-scoring template, used as-is.\n- Predictions 2–5 (when TBM fills multiple slots): sampled from the top-12 with exponential weighting. Already-used templates receive a 0.1× weight penalty to discourage duplication.\n\n**Gap filling:**\n- Aligned gaps are filled by linear interpolation between the two nearest valid C1' coordinates.\n- One-sided gaps (at chain termini) are extended by 5.95 Å steps along the extrapolated direction.\n- If no template exists at all, a fallback linear structure is placed along the X-axis at 5.95 Å steps.\n\n**Post-processing (`adaptive_rna_constraints`):**\nEach TBM prediction is refined per-chain with:\n1. Bond length correction: i→i+1 distance → 5.95 Å\n2. Angle correction: i→i+2 distance → 10.2 Å\n3. Laplacian smoothing to remove kinks\n4. Steric self-avoidance (3.2 Å threshold) for chains of length ≥ 25\n\nThe correction strength scales with `(1 − template_similarity)` so that near-identical templates are barely modified while low-similarity matches are corrected more aggressively.\n\n---\n\n## Phase 2: DRFold2\n\nDRFold2 (cfg97 configuration, 20 models) provides an RNA-specific deep-learning signal, contributing 1 prediction for sequences shorter than 250 nt.  \nFrom Part 1, we confirmed that cfg97 outperformed other DRFold2 configurations.\n\nWithin that range, the number of models run scales with sequence length:\n- L > 200 nt: 5 models `[13, 6, 14, 5, 3]`\n- L > 100 nt: 10 models `[13, 6, 14, 12, 7, 2, 5, 19, 10, 9]`\n- L ≤ 100 nt: all 20 models\n\nFor each model's output, we compute an energy score (bond lengths, bond angles, stacking) and normalize by the median absolute deviation across predictions. The top-5 scoring structures are selected.\n\n---\n\n## Phase 3: RNAPro\n\nRNAPro (NVIDIA's Part 1 winner) is used for all sequences under 1000 nt.  \nIt contributes 2 predictions for mid-range sequences (250–999 nt) and 1 prediction for short sequences (< 250 nt), each conditioned on a different TBM template (top-1 and top-2).\n\nConfiguration:\n- MSA enabled (`--use_msa true`)\n- Pre-computed TBM templates (`--use_template ca_precomputed`)\n- RibonanzaNet2 embeddings\n- N_STEP = 200, N_CYCLE = 10, N_SAMPLE = 1\n\n---\n\n## Phase 4: Boltz2\n\nBoltz2 is the primary model for short sequences (< 250 nt), contributing 2 predictions, and contributes 2 predictions for mid-range sequences (250–999 nt) as well.  \nIt is skipped for sequences ≥ 1000 nt to avoid OOM.\n\n- `diffusion_samples = 10` structures generated per target\n- Top-5 selected by combined plddt + confidence score\n- Ligand information (SMILES) included in YAML input\n- Multi-chain targets: only RNA chains are folded (`use_all_chains = False`) to avoid OOM with large complexes\n\n---\n\n## Phase 5: Protenix\n\nProtenix (ByteDance, AlphaFold3 architecture) contributes 1 prediction for short sequences (< 250 nt) and 2 predictions for very long sequences (≥ 1000 nt).\n\n- RNA MSA enabled (`USE_RNA_MSA = true`)\n\n**Long-sequence handling (≥ 1000 nt):**\n\nProtenix has a practical per-inference memory limit, so sequences longer than `MAX_SEQ_LEN = 512` nt are processed with a sliding-window chunking strategy:\n\n1. **Chunking** — `split_sequence(seq, max_len=512, overlap=128)` divides the full sequence into overlapping windows.\n   The step size is `512 − 128 = 384` nt, so a 1000 nt sequence produces three chunks: `[0:512]`, `[384:896]`, `[768:1000]`.\n\n2. **Per-chunk inference** — each chunk is fed to Protenix independently as a separate short-sequence target (its own JSON input and `InferenceDataset`).\n   `update_inference_configs` is called with the chunk token count so internal model buffers are sized correctly.\n\n3. **C1' extraction** — from each chunk's raw atom-level output, C1' atoms are identified by matching `res_id` (1-indexed within the chunk) and `atom_name == \"C1'\"`.\n   A two-stage fallback is used: first `centre_atom_mask`, then `atom_to_tokatom_idx == 12`.\n\n4. **Assembly** — extracted C1' coordinates `(N_sample, chunk_len, 3)` are written into a pre-allocated `full_coords (N_sample, seq_len, 3)` array at `[:, start:end, :]`.\n   Overlapping positions are overwritten by the later (right-side) chunk.\n\n5. **Memory cleanup** — `torch.cuda.empty_cache()` and `gc.collect()` are called after every chunk to avoid GPU OOM on very long targets.\n\n---\n\n## What Worked\n\n### The combination of five structurally diverse models.  \nFrom Part 1 we confirmed that ensembling Boltz, Protenix, and DRFold2 was robustly better on unseen sequences than any single model alone.  \nBuilding on that, Part 2 added RNAPro (the Part 1 winner) as a powerful refinement step, which significantly improved our mid-range sequences.\n\n### TBM as the strong backbone for medium and long sequences.  \nTBM proved highly competitive whenever a similar sequence existed in the training data.  \nFor sequences ≥ 250 nt, allocating multiple predictions to TBM and using other models to cover the remaining predictions was consistently better than the reverse.\n\n### Length-adaptive allocation.\nRather than a one-size-fits-all ensemble, we tuned how many predictions each model contributes based on empirical performance at each length range.  \nThe \"overlay\" structure of the pipeline (models are run in order and later models overwrite earlier ones) made this easy to tune incrementally.  \nThe 250 nt boundary was selected by balancing inference time against score: models like Boltz2 and DRFold2 are fast enough for short sequences within the time limit but become impractical beyond this point, while TBM scales well to longer sequences at low cost.\n\n### Diversity over TBM dependency.  \nWe treated TBM as a backbone only where it is clearly strongest (longer sequences with close training-set matches), and filled the remaining predictions with diverse models.  \nFor short sequences (< 250 nt), we deliberately avoided TBM as the primary predictor and instead relied on Boltz2, DRFold2, and Protenix — models that make predictions purely from sequence without template dependency.  \nFor the remaining slots outside of short sequences, we combined RNAPro — which starts from a TBM template but refines it into an independently generated structure — with template-free models (Boltz2 and Protenix), ensuring diversity across all five predictions.  \nWe believe this diversity contributed to our performance on the private leaderboard, which contained harder targets where no close template existed.\n\n---\n\n## Authors\n\nteam_cp: @naganohikaru, @yutaroito\n\n---\n\n## References\n\n- [Our Part 1 solution (25th place)](https://www.kaggle.com/competitions/stanford-rna-3d-folding/writeups/25th-place-solution) — baseline ensemble strategy and lessons learned carried into Part 2.\n- [Part 2 solution discussion](https://www.kaggle.com/competitions/stanford-rna-3d-folding-2/discussion/668412) — competition discussion thread for this solution.\n- [Protenix v1 inference notebook](https://www.kaggle.com/code/qiweiyin/protenix-v1-inference-2026) — public notebook that formed the basis of our Protenix integration.\n- [Beginner-to-advanced RNA 3D structure prediction](https://www.kaggle.com/code/qamarmath/beginner-to-advanced-rna-3d-structure-predicti) — general pipeline reference used during development.\n",
      "votes": 25
    },
    {
      "id": 3444138,
      "postDate": "2026-04-17T11:07:16.097Z",
      "content": "<p>This is a very elegant ensemble design\nEspecially the length-adaptive allocation strategy</p>",
      "rawMarkdown": "This is a very elegant ensemble design\nEspecially the length-adaptive allocation strategy",
      "votes": -1
    },
    {
      "id": 3505485,
      "postDate": "2026-07-30T08:12:21.693Z",
      "content": "<p>Implausable</p>",
      "rawMarkdown": "Implausable\n"
    },
    {
      "id": 3463809,
      "postDate": "2026-05-27T23:34:49.287Z",
      "content": "<p>Great write up!  Can you by any chance share the csv of the submission for this one.  Think I can hyper param on it a little and take it from there (?)</p>",
      "rawMarkdown": "Great write up!  Can you by any chance share the csv of the submission for this one.  Think I can hyper param on it a little and take it from there (?)",
      "replies": [
        {
          "id": 3464174,
          "postDate": "2026-05-29T03:44:51.533Z",
          "content": "<p>Thanks for the comment! As this is a code-only competition, I don't actually have the CSV file with me. It’d be best to run the kernel from the write-up directly on Kaggle and get the output from there!</p>",
          "rawMarkdown": "Thanks for the comment! As this is a code-only competition, I don't actually have the CSV file with me. It’d be best to run the kernel from the write-up directly on Kaggle and get the output from there!"
        }
      ]
    },
    {
      "id": 3442665,
      "postDate": "2026-04-15T18:49:02.760Z",
      "content": "<p>congrats Brothers</p>",
      "rawMarkdown": "congrats Brothers"
    },
    {
      "id": 3438322,
      "postDate": "2026-04-08T23:48:51.373Z",
      "content": "<p>Excellent work!</p>",
      "rawMarkdown": "Excellent work!"
    },
    {
      "id": 3438072,
      "postDate": "2026-04-08T16:11:08.020Z",
      "content": "<p>Congrats! Impressive how your team managed to run 5 models in 8 hours. I tried but always got time out. After reading the writeup I realize you have much better routing strategy than I did :p</p>",
      "rawMarkdown": "Congrats! Impressive how your team managed to run 5 models in 8 hours. I tried but always got time out. After reading the writeup I realize you have much better routing strategy than I did :p"
    }
  ],
  "comments": [
    {
      "id": 3444138,
      "author_name": "Durga Kumari",
      "author_url": "",
      "post_date": "2026-04-17T11:07:16.097000",
      "content": "<p>This is a very elegant ensemble design\nEspecially the length-adaptive allocation strategy</p>",
      "votes": -1,
      "replies": []
    },
    {
      "id": 3505485,
      "author_name": "Sayon Saha",
      "author_url": "",
      "post_date": "2026-07-30T08:12:21.693000",
      "content": "<p>Implausable</p>",
      "votes": 0,
      "replies": []
    },
    {
      "id": 3463809,
      "author_name": "Khaled",
      "author_url": "",
      "post_date": "2026-05-27T23:34:49.287000",
      "content": "<p>Great write up!  Can you by any chance share the csv of the submission for this one.  Think I can hyper param on it a little and take it from there (?)</p>",
      "votes": 0,
      "replies": [
        {
          "id": 3464174,
          "author_name": "k2011yi",
          "author_url": "",
          "post_date": "2026-05-29T03:44:51.533000",
          "content": "<p>Thanks for the comment! As this is a code-only competition, I don't actually have the CSV file with me. It’d be best to run the kernel from the write-up directly on Kaggle and get the output from there!</p>",
          "votes": 0,
          "replies": []
        }
      ]
    },
    {
      "id": 3442665,
      "author_name": "Hafiz Ali Shahid",
      "author_url": "",
      "post_date": "2026-04-15T18:49:02.760000",
      "content": "<p>congrats Brothers</p>",
      "votes": 0,
      "replies": []
    },
    {
      "id": 3438322,
      "author_name": "Qiwei",
      "author_url": "",
      "post_date": "2026-04-08T23:48:51.373000",
      "content": "<p>Excellent work!</p>",
      "votes": 0,
      "replies": []
    },
    {
      "id": 3438072,
      "author_name": "hongan",
      "author_url": "",
      "post_date": "2026-04-08T16:11:08.020000",
      "content": "<p>Congrats! Impressive how your team managed to run 5 models in 8 hours. I tried but always got time out. After reading the writeup I realize you have much better routing strategy than I did :p</p>",
      "votes": 0,
      "replies": []
    }
  ],
  "raw_markdown_by_id": {
    "3438018": "## Acknowledgements\n\nWe are team_cp ( @naganohikaru, @yutaroito), a two-person team.  \nThis is our second time participating in the Stanford RNA 3D Folding series; we placed 25th in Part 1.  \nThe experience from Part 1 — particularly understanding which model combinations held up on unseen data and learning the power of template-based modeling — gave us a strong foundation for this competition.  \n  \nWe are deeply grateful to the competition organizers, Stanford University, and the many Kagglers who shared public notebooks and insights throughout the competition!\n\n---\n\n## Summary\n\nOur solution combines five independent structure prediction models into a single 5-prediction submission, with each model's allocation driven by sequence length.  \nSince scoring is best-of-5, the goal is to maximize structural diversity across the five predictions.   \n### The five models are:\n\n| Model | Role |\n|---|---|\n| **TBM** (Template-Based Modeling) | Primary predictor for seq_len ≥ 250; fallback for all lengths |\n| **Boltz2** | Primary predictor for seq_len < 250; secondary for 250–999 |\n| **RNAPro** | Diffusion-based refinement for seq_len < 1000 |\n| **DRFold2** | RNA-specific deep learning for short sequences |\n| **Protenix** | AlphaFold3-based; short sequences and ≥ 1000 nt |\n  \n  \n### Final ensemble composition (5 predictions per target):\n| seq_len | Pred 1 | Pred 2 | Pred 3 | Pred 4 | Pred 5 |\n|---|---|---|---|---|---|\n| < 250 | Boltz2₁ | Boltz2₂ | RNApro₁ | Protenix₁ | DRFold2₁ |\n| 250 – 999 | TBM₁ | Boltz2₁ | RNApro₁ | RNApro₂ | Boltz2₂ |\n| ≥ 1000 | TBM₁ | TBM₂ | TBM₃ | Protenix₁ | Protenix₂ |\n\nRNApro and Boltz2 skip sequences ≥ 1000 nt (OOM risk), so the ≥ 1000 nt tier uses TBM for 3 predictions and Protenix for the remaining 2.\n\n### Final scores (selected submission):\n\n| Comp. Public LB | Comp. Private LB | Final Public LB | Final Private LB |\n|---|---|---|---|\n| 0.43837 | 0.60037 | 0.42854 | **0.49669** |\n\n---\n\n## Phase 1: Template-Based Modeling (TBM)\n\nTBM is the backbone of our pipeline for medium and long sequences.  \nWe search a combined train + validation pool using BioPython's `PairwiseAligner` (global mode), filtering to templates whose length is within 30% of the query length. Alignments are scored and normalized; the top-30 templates form the candidate pool.\n\n**Diversity within TBM predictions:**\n- Prediction 1: top-scoring template, used as-is.\n- Predictions 2–5 (when TBM fills multiple slots): sampled from the top-12 with exponential weighting. Already-used templates receive a 0.1× weight penalty to discourage duplication.\n\n**Gap filling:**\n- Aligned gaps are filled by linear interpolation between the two nearest valid C1' coordinates.\n- One-sided gaps (at chain termini) are extended by 5.95 Å steps along the extrapolated direction.\n- If no template exists at all, a fallback linear structure is placed along the X-axis at 5.95 Å steps.\n\n**Post-processing (`adaptive_rna_constraints`):**\nEach TBM prediction is refined per-chain with:\n1. Bond length correction: i→i+1 distance → 5.95 Å\n2. Angle correction: i→i+2 distance → 10.2 Å\n3. Laplacian smoothing to remove kinks\n4. Steric self-avoidance (3.2 Å threshold) for chains of length ≥ 25\n\nThe correction strength scales with `(1 − template_similarity)` so that near-identical templates are barely modified while low-similarity matches are corrected more aggressively.\n\n---\n\n## Phase 2: DRFold2\n\nDRFold2 (cfg97 configuration, 20 models) provides an RNA-specific deep-learning signal, contributing 1 prediction for sequences shorter than 250 nt.  \nFrom Part 1, we confirmed that cfg97 outperformed other DRFold2 configurations.\n\nWithin that range, the number of models run scales with sequence length:\n- L > 200 nt: 5 models `[13, 6, 14, 5, 3]`\n- L > 100 nt: 10 models `[13, 6, 14, 12, 7, 2, 5, 19, 10, 9]`\n- L ≤ 100 nt: all 20 models\n\nFor each model's output, we compute an energy score (bond lengths, bond angles, stacking) and normalize by the median absolute deviation across predictions. The top-5 scoring structures are selected.\n\n---\n\n## Phase 3: RNAPro\n\nRNAPro (NVIDIA's Part 1 winner) is used for all sequences under 1000 nt.  \nIt contributes 2 predictions for mid-range sequences (250–999 nt) and 1 prediction for short sequences (< 250 nt), each conditioned on a different TBM template (top-1 and top-2).\n\nConfiguration:\n- MSA enabled (`--use_msa true`)\n- Pre-computed TBM templates (`--use_template ca_precomputed`)\n- RibonanzaNet2 embeddings\n- N_STEP = 200, N_CYCLE = 10, N_SAMPLE = 1\n\n---\n\n## Phase 4: Boltz2\n\nBoltz2 is the primary model for short sequences (< 250 nt), contributing 2 predictions, and contributes 2 predictions for mid-range sequences (250–999 nt) as well.  \nIt is skipped for sequences ≥ 1000 nt to avoid OOM.\n\n- `diffusion_samples = 10` structures generated per target\n- Top-5 selected by combined plddt + confidence score\n- Ligand information (SMILES) included in YAML input\n- Multi-chain targets: only RNA chains are folded (`use_all_chains = False`) to avoid OOM with large complexes\n\n---\n\n## Phase 5: Protenix\n\nProtenix (ByteDance, AlphaFold3 architecture) contributes 1 prediction for short sequences (< 250 nt) and 2 predictions for very long sequences (≥ 1000 nt).\n\n- RNA MSA enabled (`USE_RNA_MSA = true`)\n\n**Long-sequence handling (≥ 1000 nt):**\n\nProtenix has a practical per-inference memory limit, so sequences longer than `MAX_SEQ_LEN = 512` nt are processed with a sliding-window chunking strategy:\n\n1. **Chunking** — `split_sequence(seq, max_len=512, overlap=128)` divides the full sequence into overlapping windows.\n   The step size is `512 − 128 = 384` nt, so a 1000 nt sequence produces three chunks: `[0:512]`, `[384:896]`, `[768:1000]`.\n\n2. **Per-chunk inference** — each chunk is fed to Protenix independently as a separate short-sequence target (its own JSON input and `InferenceDataset`).\n   `update_inference_configs` is called with the chunk token count so internal model buffers are sized correctly.\n\n3. **C1' extraction** — from each chunk's raw atom-level output, C1' atoms are identified by matching `res_id` (1-indexed within the chunk) and `atom_name == \"C1'\"`.\n   A two-stage fallback is used: first `centre_atom_mask`, then `atom_to_tokatom_idx == 12`.\n\n4. **Assembly** — extracted C1' coordinates `(N_sample, chunk_len, 3)` are written into a pre-allocated `full_coords (N_sample, seq_len, 3)` array at `[:, start:end, :]`.\n   Overlapping positions are overwritten by the later (right-side) chunk.\n\n5. **Memory cleanup** — `torch.cuda.empty_cache()` and `gc.collect()` are called after every chunk to avoid GPU OOM on very long targets.\n\n---\n\n## What Worked\n\n### The combination of five structurally diverse models.  \nFrom Part 1 we confirmed that ensembling Boltz, Protenix, and DRFold2 was robustly better on unseen sequences than any single model alone.  \nBuilding on that, Part 2 added RNAPro (the Part 1 winner) as a powerful refinement step, which significantly improved our mid-range sequences.\n\n### TBM as the strong backbone for medium and long sequences.  \nTBM proved highly competitive whenever a similar sequence existed in the training data.  \nFor sequences ≥ 250 nt, allocating multiple predictions to TBM and using other models to cover the remaining predictions was consistently better than the reverse.\n\n### Length-adaptive allocation.\nRather than a one-size-fits-all ensemble, we tuned how many predictions each model contributes based on empirical performance at each length range.  \nThe \"overlay\" structure of the pipeline (models are run in order and later models overwrite earlier ones) made this easy to tune incrementally.  \nThe 250 nt boundary was selected by balancing inference time against score: models like Boltz2 and DRFold2 are fast enough for short sequences within the time limit but become impractical beyond this point, while TBM scales well to longer sequences at low cost.\n\n### Diversity over TBM dependency.  \nWe treated TBM as a backbone only where it is clearly strongest (longer sequences with close training-set matches), and filled the remaining predictions with diverse models.  \nFor short sequences (< 250 nt), we deliberately avoided TBM as the primary predictor and instead relied on Boltz2, DRFold2, and Protenix — models that make predictions purely from sequence without template dependency.  \nFor the remaining slots outside of short sequences, we combined RNAPro — which starts from a TBM template but refines it into an independently generated structure — with template-free models (Boltz2 and Protenix), ensuring diversity across all five predictions.  \nWe believe this diversity contributed to our performance on the private leaderboard, which contained harder targets where no close template existed.\n\n---\n\n## Authors\n\nteam_cp: @naganohikaru, @yutaroito\n\n---\n\n## References\n\n- [Our Part 1 solution (25th place)](https://www.kaggle.com/competitions/stanford-rna-3d-folding/writeups/25th-place-solution) — baseline ensemble strategy and lessons learned carried into Part 2.\n- [Part 2 solution discussion](https://www.kaggle.com/competitions/stanford-rna-3d-folding-2/discussion/668412) — competition discussion thread for this solution.\n- [Protenix v1 inference notebook](https://www.kaggle.com/code/qiweiyin/protenix-v1-inference-2026) — public notebook that formed the basis of our Protenix integration.\n- [Beginner-to-advanced RNA 3D structure prediction](https://www.kaggle.com/code/qamarmath/beginner-to-advanced-rna-3d-structure-predicti) — general pipeline reference used during development.\n",
    "3444138": "This is a very elegant ensemble design\nEspecially the length-adaptive allocation strategy",
    "3505485": "Implausable\n",
    "3463809": "Great write up!  Can you by any chance share the csv of the submission for this one.  Think I can hyper param on it a little and take it from there (?)",
    "3442665": "congrats Brothers",
    "3438322": "Excellent work!",
    "3438072": "Congrats! Impressive how your team managed to run 5 models in 8 hours. I tried but always got time out. After reading the writeup I realize you have much better routing strategy than I did :p"
  }
}