From 2d5147419234314cc6912273801f76e4c07c855f Mon Sep 17 00:00:00 2001 From: "google-labs-jules[bot]" <161369871+google-labs-jules[bot]@users.noreply.github.com> Date: Tue, 4 Aug 2026 08:59:29 +0000 Subject: [PATCH] =?UTF-8?q?=E2=9A=A1=20Bolt:=20[performance=20improvement]?= =?UTF-8?q?=20Optimize=20SplitFlapDisplay=20rendering?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: nickdesi <38331055+nickdesi@users.noreply.github.com> --- .jules/bolt.md | 4 ++++ src/components/SplitFlapDisplay.tsx | 36 ++++++++++++++++++----------- 2 files changed, 27 insertions(+), 13 deletions(-) diff --git a/.jules/bolt.md b/.jules/bolt.md index 00b428bc..abad5a70 100644 --- a/.jules/bolt.md +++ b/.jules/bolt.md @@ -104,3 +104,7 @@ ## $(date +%Y-%m-%d) - Avoiding redundant normalization computations **Learning:** Functions like `normalizeText` which rely on `.normalize('NFD')` and regular expressions `.replace(/[\u0300-\u036f]/g, '')` are computationally expensive, and in large lists or during data mapping they can be called thousands of times on the same few strings (e.g., destinations like 'AUBIÈRE' or 'GERZAT'). This redundant computation causes CPU bottlenecks and garbage collection overhead. **Action:** Use a simple module-level `Map` to cache the results of computationally expensive string operations like `normalizeText`. For fields like transit destinations, the number of unique strings is very small, making a cache highly memory-efficient while significantly reducing CPU work. + +## 2026-07-28 - String Split and Map Anti-Pattern in React Render Loop +**Learning:** Found an anti-pattern in `SplitFlapDisplay.tsx` where `text.split('').map(...)` was used inside a highly reused memoized component's render function. This causes the JavaScript engine to allocate an intermediate array of single-character strings on every render, leading to unnecessary memory churn and garbage collection pressure, particularly when rendering many list items or table rows. +**Action:** Replace `text.split('').map(...)` with a `for` loop (e.g. `for (let idx = 0; idx < text.length; idx++)`) and directly push the mapped JSX elements to a pre-allocated array. This avoids the intermediate string array allocation completely. diff --git a/src/components/SplitFlapDisplay.tsx b/src/components/SplitFlapDisplay.tsx index 70890c01..0a7e3123 100644 --- a/src/components/SplitFlapDisplay.tsx +++ b/src/components/SplitFlapDisplay.tsx @@ -6,22 +6,32 @@ interface SplitFlapDisplayProps { color?: string; } +// ⚡ Bolt: Removed text.split('').map() which creates an intermediate array of strings +// on every render. Replaced with a single-pass loop over the string characters to reduce +// memory allocation and garbage collection overhead, especially important as this component +// is rendered heavily in lists and tables. const SplitFlapDisplay = memo(function SplitFlapDisplay({ text, size = 'xl', color = 'text-yellow-500' }: SplitFlapDisplayProps) { - const chars = text.split(''); + const chars = []; + for (let idx = 0; idx < text.length; idx++) { + // eslint-disable-next-line security/detect-object-injection + const char = text[idx]; + chars.push( + + {char} + + ); + } + return (