<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Shohruh Sharipov</title>
    <description>The latest articles on DEV Community by Shohruh Sharipov (@shohruh_sharipov).</description>
    <link>https://dev.to/shohruh_sharipov</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F3713207%2F94e8d4b1-a39e-45fe-a6e2-ddbeb09fbadb.jpg</url>
      <title>DEV Community: Shohruh Sharipov</title>
      <link>https://dev.to/shohruh_sharipov</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/shohruh_sharipov"/>
    <language>en</language>
    <item>
      <title>How HashMap Really Works in Java (Under the Hood)</title>
      <dc:creator>Shohruh Sharipov</dc:creator>
      <pubDate>Fri, 04 Sep 2026 18:18:28 +0000</pubDate>
      <link>https://dev.to/shohruh_sharipov/how-hashmap-really-works-in-java-under-the-hood-6a1</link>
      <guid>https://dev.to/shohruh_sharipov/how-hashmap-really-works-in-java-under-the-hood-6a1</guid>
      <description>&lt;p&gt;Every Java developer uses HashMap. Far fewer can explain what actually happens when you call put() or get(). Here's what's going on under the hood.&lt;/p&gt;

&lt;p&gt;I animated the whole thing below 👇 — writeup underneath.&lt;/p&gt;

&lt;p&gt;  &lt;iframe src="https://www.youtube.com/embed/8GtbRf1NqZ4" width="710" height="399"&gt;
  &lt;/iframe&gt;
&lt;/p&gt;

&lt;h2&gt;
  
  
  From key to bucket
&lt;/h2&gt;

&lt;p&gt;When you put a key in:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;HashMap calls the key's hashCode() to get an int.&lt;/li&gt;
&lt;li&gt;It spreads the bits (to reduce clustering) and maps it to one of N buckets — essentially hash &amp;amp; (N - 1).&lt;/li&gt;
&lt;li&gt;The entry is stored in that bucket.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;get() runs the same math to jump straight to the right bucket. That's why average lookups are O(1) — no scanning the whole map.&lt;/p&gt;

&lt;h2&gt;
  
  
  Collisions
&lt;/h2&gt;

&lt;p&gt;Two different keys can land in the same bucket. HashMap handles this with separate chaining — a linked list inside the bucket. Since Java 8, once a single bucket gets long enough (8+ entries), it converts that list into a balanced tree, so a worst-case bad-hash scenario degrades to O(log n) instead of O(n).&lt;/p&gt;

&lt;h2&gt;
  
  
  Resizing (rehashing)
&lt;/h2&gt;

&lt;p&gt;A HashMap has a load factor (default 0.75). Once it's ~75% full, it doubles the bucket array and rehashes every entry into the bigger table. This keeps buckets short and lookups fast — but a resize is an expensive, occasional cost.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why it matters in practice
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;equals() and hashCode() must agree.&lt;/strong&gt; Break that contract and keys effectively "disappear" — you store with one and can't retrieve with an equal one.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Size it up front&lt;/strong&gt; for large inserts (&lt;code&gt;new HashMap&amp;lt;&amp;gt;(expectedSize)&lt;/code&gt;) to avoid repeated resizes.&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;I make animated breakdowns like this — data structures, system design &amp;amp; backend, visualized — on &lt;strong&gt;CodeAnimated&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;▶ Full channel: &lt;a href="https://www.youtube.com/@CodeAnimatedDev" rel="noopener noreferrer"&gt;https://www.youtube.com/@CodeAnimatedDev&lt;/a&gt;&lt;/p&gt;

</description>
      <category>java</category>
      <category>datastructures</category>
      <category>programming</category>
      <category>computerscience</category>
    </item>
    <item>
      <title>Why Your Counter Shows 847 Instead of 1000 (Race Conditions, Explained)</title>
      <dc:creator>Shohruh Sharipov</dc:creator>
      <pubDate>Fri, 04 Sep 2026 18:08:35 +0000</pubDate>
      <link>https://dev.to/shohruh_sharipov/why-your-counter-shows-847-instead-of-1000-race-conditions-explained-402a</link>
      <guid>https://dev.to/shohruh_sharipov/why-your-counter-shows-847-instead-of-1000-race-conditions-explained-402a</guid>
      <description>&lt;p&gt;Two threads each increment a shared counter 1,000 times. You expect 2,000. You run it — and get 1,847. Where did the missing increments go?&lt;/p&gt;

&lt;p&gt;I animated exactly what happens below 👇 — the writeup is underneath.&lt;/p&gt;

&lt;p&gt;  &lt;iframe src="https://www.youtube.com/embed/ZugvFze-2j0" width="710" height="399"&gt;
  &lt;/iframe&gt;
&lt;/p&gt;

&lt;h2&gt;
  
  
  Why &lt;code&gt;count++&lt;/code&gt; isn't safe
&lt;/h2&gt;

&lt;p&gt;&lt;code&gt;count++&lt;/code&gt; looks like one operation. It's actually three:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;READ&lt;/strong&gt; the current value&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;ADD&lt;/strong&gt; 1&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;WRITE&lt;/strong&gt; it back&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Between any two of those steps, another thread can jump in. Both threads read the same value, both add 1, both write the same result — and one increment is silently lost. Do that thousands of times across two threads and you land below 2,000.&lt;/p&gt;

&lt;h2&gt;
  
  
  Three ways to fix it
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;&lt;code&gt;synchronized&lt;/code&gt;&lt;/strong&gt; — only one thread in the critical section at a time. Simple, correct, a little heavy.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;code&gt;AtomicInteger&lt;/code&gt;&lt;/strong&gt; — lock-free, backed by a CPU compare-and-swap. Best for counters: &lt;code&gt;counter.incrementAndGet()&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;code&gt;ReentrantLock&lt;/code&gt;&lt;/strong&gt; — explicit &lt;code&gt;lock()&lt;/code&gt; / &lt;code&gt;unlock()&lt;/code&gt; when you need finer control.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Why race conditions are so nasty
&lt;/h2&gt;

&lt;p&gt;They almost never show up in single-threaded tests. They only appear under real concurrency, under load — which is why they slip into production and are miserable to reproduce. If shared, mutable state is touched by more than one thread, it must be synchronized.&lt;/p&gt;




&lt;p&gt;I make animated breakdowns like this — concurrency, system design &amp;amp; backend, visualized — on &lt;strong&gt;CodeAnimated&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;▶ Full channel: &lt;a href="https://www.youtube.com/@CodeAnimatedDev" rel="noopener noreferrer"&gt;https://www.youtube.com/@CodeAnimatedDev&lt;/a&gt;&lt;/p&gt;

</description>
      <category>java</category>
      <category>concurrency</category>
      <category>programming</category>
      <category>beginners</category>
    </item>
    <item>
      <title>How Banks Detect Fraud in 27 Milliseconds (The System Design)</title>
      <dc:creator>Shohruh Sharipov</dc:creator>
      <pubDate>Fri, 04 Sep 2026 17:54:44 +0000</pubDate>
      <link>https://dev.to/shohruh_sharipov/how-banks-detect-fraud-in-27-milliseconds-the-system-design-1ldk</link>
      <guid>https://dev.to/shohruh_sharipov/how-banks-detect-fraud-in-27-milliseconds-the-system-design-1ldk</guid>
      <description>&lt;p&gt;You tap your card in New York. Two minutes later, someone tries to use it in Lagos — and the bank blocks it instantly. How does it decide in under 30 milliseconds, across billions of transactions a day?&lt;/p&gt;

&lt;p&gt;I animated the whole pipeline below 👇 — the rest of this post walks through it in text.&lt;/p&gt;

&lt;p&gt;  &lt;iframe src="https://www.youtube.com/embed/QFzwbTFur5w" width="710" height="399"&gt;
  &lt;/iframe&gt;
&lt;/p&gt;

&lt;h2&gt;
  
  
  The 5-stage pipeline (~27ms total)
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;1. Ingest — Apache Kafka (~1ms).&lt;/strong&gt; Millions of transactions per second stream in. Kafka appends each to a log, so nothing is lost and everything is processed in real time.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;2. Rules engine (~2ms).&lt;/strong&gt; Fast, hard-coded checks run first: geo-velocity (NYC → Lagos in 2 minutes = physically impossible), amount vs. the user's historical average, and time-of-day / spending-limit patterns.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;3. ML model (~15ms).&lt;/strong&gt; The heavy lifting. A model trained on 500M+ real transactions takes features — amount, geo distance, merchant category, device fingerprint — and outputs a fraud probability score.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;4. Graph database (~8ms).&lt;/strong&gt; Checks whether this card, merchant, or device is connected to known fraud rings. One fraudster's network can span thousands of cards, and a graph query surfaces that instantly.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;5. Decision engine (~1ms).&lt;/strong&gt; Combine the signals into a score:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;0–30 → auto-approve&lt;/li&gt;
&lt;li&gt;31–69 → send an OTP challenge&lt;/li&gt;
&lt;li&gt;70–89 → human analyst queue&lt;/li&gt;
&lt;li&gt;90–100 → instant block + SMS alert&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;A combined score of 94/100 means BLOCKED, and the cardholder is notified in about a second.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why it's fast
&lt;/h2&gt;

&lt;p&gt;Every slow decision is pushed off the critical path: Kafka absorbs bursts, the rules engine kills obvious cases before the ML model ever runs, and scoring is precomputed features plus fast inference — never a big database scan on the hot path.&lt;/p&gt;




&lt;p&gt;I make animated breakdowns like this — system design, backend &amp;amp; DevOps, visualized — on &lt;strong&gt;CodeAnimated&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;▶ Full channel: &lt;a href="https://www.youtube.com/@CodeAnimatedDev" rel="noopener noreferrer"&gt;https://www.youtube.com/@CodeAnimatedDev&lt;/a&gt;&lt;/p&gt;

</description>
      <category>systemdesign</category>
      <category>programming</category>
      <category>backend</category>
      <category>computerscience</category>
    </item>
    <item>
      <title>Free developer online tools</title>
      <dc:creator>Shohruh Sharipov</dc:creator>
      <pubDate>Fri, 27 Feb 2026 10:27:36 +0000</pubDate>
      <link>https://dev.to/shohruh_sharipov/free-developer-online-tools-1mh5</link>
      <guid>https://dev.to/shohruh_sharipov/free-developer-online-tools-1mh5</guid>
      <description>&lt;p&gt;I built DevUtilities.dev — 16 free developer tools, no sign-up, everything runs in your browser.&lt;br&gt;
Tired of pasting JWTs into sketchy sites with cookie banners and pop-ups. So I built my own: JWT decoder, JSON formatter, regex tester, UUID generator, YAML↔JSON converter, QR code generator, cron builder and more.&lt;br&gt;
Your data never leaves your machine. No account needed. Just open and use.&lt;br&gt;
👉 &lt;a href="https://devutilities.dev" rel="noopener noreferrer"&gt;https://devutilities.dev&lt;/a&gt;&lt;br&gt;
What tools do you wish existed? Drop them in the comments.&lt;/p&gt;

&lt;p&gt;Tags: #webdev #tools #productivity #javascript&lt;/p&gt;

</description>
      <category>productivity</category>
      <category>showdev</category>
      <category>tooling</category>
      <category>webdev</category>
    </item>
  </channel>
</rss>
