{"id":1184,"date":"2026-02-27T22:03:38","date_gmt":"2026-02-27T22:03:38","guid":{"rendered":"https:\/\/inphronesys.com\/?p=1184"},"modified":"2026-02-27T22:03:38","modified_gmt":"2026-02-27T22:03:38","slug":"stop-the-madness-why-your-mrp-keeps-changing-its-mind-and-how-time-fences-fix-it","status":"publish","type":"post","link":"https:\/\/inphronesys.com\/?p=1184","title":{"rendered":"Stop the Madness: Why Your MRP Keeps Changing Its Mind (and How Time Fences Fix It)"},"content":{"rendered":"<h2>Monday Morning, 6:47 AM<\/h2>\n<p>Klaus manages production planning at a mid-size automotive parts manufacturer. Every Monday, he arrives to find MRP has run overnight and produced a fresh batch of action messages. This Monday: 347 reschedule recommendations. Twelve cancellations. Eight new rush orders. Five items that were rush orders <em>last<\/em> week are now marked &#8222;cancel.&#8220;<\/p>\n<p>By 9 AM, the shop floor supervisor storms into his office. &#8222;Klaus, you told us Friday to set up Line 3 for the 4200-series housing. We ran overtime Saturday to make the changeover. Now the system says cancel it and switch to the 7100-series bracket?&#8220;<\/p>\n<p>The setup cost $2,800. The overtime cost $4,500. The 7100-series bracket will probably get rescheduled again by Wednesday.<\/p>\n<p>Klaus doesn&#8217;t argue. He&#8217;s seen this movie before. Every week, MRP faithfully recalculates the plan based on the latest demand signals, and every week, the plan looks nothing like last week&#8217;s plan. The shop floor has learned to treat MRP output like weather forecasts \u2014 interesting, but not something you&#8217;d bet your weekend on.<\/p>\n<p>This is <strong>planning nervousness<\/strong>, and it is one of the most expensive and least discussed problems in manufacturing. Every reschedule costs money: setup changes, expediting fees, overtime, supplier penalties, and \u2014 hardest to quantify but very real \u2014 the slow erosion of trust between planning and execution. When the shop floor stops believing the plan, you don&#8217;t have a planning system anymore. You have a suggestion box.<\/p>\n<p>The fix is older than ERP software itself. It&#8217;s called <strong>time fences<\/strong>, and the math behind optimal fence positioning is surprisingly elegant.<\/p>\n<h2>What Are Time Fences?<\/h2>\n<p>A time fence is a boundary on the planning timeline that controls <em>who<\/em> can change <em>what<\/em> and <em>when<\/em>. Think of it as a set of traffic signals for your master production schedule (MPS). Near-term plans need stability so production can execute. Long-term plans need flexibility so planning can respond to demand shifts. Time fences define where stability ends and flexibility begins.<\/p>\n<p>The standard model uses three zones:<\/p>\n<p><img decoding=\"async\" src=\"https:\/\/inphronesys.com\/wp-content\/uploads\/2026\/02\/tf_fence_zones-2.png\" alt=\"Time fence zones in production planning\" \/><\/p>\n<h3>The Frozen Zone (Demand Fence)<\/h3>\n<p><strong>Period: Weeks 1-4 in our example (typically 2-6 weeks, depending on cumulative lead time)<\/strong><\/p>\n<p>Inside the frozen zone, the schedule is locked. MRP is not allowed to reschedule, cancel, or add orders without explicit executive or senior management approval. The production plan is treated as a commitment, not a suggestion.<\/p>\n<p>Why? Because inside this window, materials have been ordered, machine setups have been scheduled, labor has been assigned, and suppliers are already executing. Changing the plan now doesn&#8217;t just cost money \u2014 it wastes money that&#8217;s already been spent.<\/p>\n<p><strong>Rules:<\/strong> No changes without VP\/plant manager sign-off. MRP generates action messages but they are <em>informational only<\/em> \u2014 they don&#8217;t trigger automatic replanning.<\/p>\n<h3>The Slushy Zone (Trading Zone)<\/h3>\n<p><strong>Period: Weeks 5-8 in our example (typically spans 2-8 weeks beyond the frozen fence)<\/strong><\/p>\n<p>The slushy zone allows controlled flexibility. The master scheduler can make changes \u2014 substituting one product for another, adjusting quantities, shifting dates by a few days \u2014 but within guidelines. Changes require planner approval and a documented justification.<\/p>\n<p>This is where the real art of production planning happens. A customer calls with an urgent order? The planner evaluates the trade-off: can we accommodate it by shifting something else, or would the cascade of changes cost more than the order is worth?<\/p>\n<p><strong>Rules:<\/strong> Changes with planner approval. Additions are generally acceptable; cancellations require review. Net change to capacity utilization must stay within +\/-10% (typical threshold).<\/p>\n<h3>The Liquid Zone (Planning Zone)<\/h3>\n<p><strong>Period: Weeks 9-16+ in our example (extends to your full planning horizon)<\/strong><\/p>\n<p>Beyond the planning fence, MRP has free rein. It can add, cancel, reschedule, and rebalance to its silicon heart&#8217;s content. This is where forecast-driven planning belongs \u2014 far enough out that changes cost nothing but electrons, and close enough that you&#8217;re preparing the supply pipeline.<\/p>\n<p><strong>Rules:<\/strong> MRP runs freely. Planners review for reasonableness but don&#8217;t manually intervene.<\/p>\n<h2>The Math: Quantifying Planning Nervousness<\/h2>\n<p>Planning nervousness isn&#8217;t just a feeling \u2014 it&#8217;s measurable. The most widely used metric is the <strong>Schedule Instability Ratio (SIR)<\/strong>, introduced by Sridharan, Berry, and Udayabhanu (1988):<\/p>\n<p><strong>SIR = (1\/T) x SUM |Q_t,i &#8211; Q_{t-1,i}| \/ SUM Q_{t-1,i}<\/strong><\/p>\n<p>Where Q_t,i is the planned quantity for period <em>i<\/em> at planning cycle <em>t<\/em>, and Q_{t-1,i} is the planned quantity for the same period <em>i<\/em> at the <em>previous<\/em> planning cycle. In plain English: what fraction of the plan changed since the last time MRP ran?<\/p>\n<p>A SIR of 0 means perfect stability \u2014 the plan never changes. A SIR of 1.0 means total chaos \u2014 the plan is completely different every time MRP runs. In practice:<\/p>\n<table>\n<thead>\n<tr>\n<th style=\"text-align: center;\">SIR Value<\/th>\n<th style=\"text-align: left;\">Interpretation<\/th>\n<th style=\"text-align: left;\">Shop Floor Reality<\/th>\n<\/tr>\n<\/thead>\n<tbody>\n<tr>\n<td style=\"text-align: center;\">&lt; 0.05<\/td>\n<td style=\"text-align: left;\">Excellent stability<\/td>\n<td style=\"text-align: left;\">&#8222;The plan is the plan. We execute.&#8220;<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: center;\">0.05 &#8211; 0.15<\/td>\n<td style=\"text-align: left;\">Acceptable<\/td>\n<td style=\"text-align: left;\">&#8222;A few changes per week, manageable.&#8220;<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: center;\">0.15 &#8211; 0.30<\/td>\n<td style=\"text-align: left;\">Problematic<\/td>\n<td style=\"text-align: left;\">&#8222;We check the plan but trust our gut.&#8220;<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: center;\">0.30 &#8211; 0.50<\/td>\n<td style=\"text-align: left;\">Severe<\/td>\n<td style=\"text-align: left;\">&#8222;MRP is a joke. We run our own schedule.&#8220;<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: center;\">&gt; 0.50<\/td>\n<td style=\"text-align: left;\">Catastrophic<\/td>\n<td style=\"text-align: left;\">&#8222;What plan?&#8220;<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<p>In practice, many manufacturing environments operate with a SIR in the <strong>0.20-0.30<\/strong> range \u2014 firmly in &#8222;problematic&#8220; territory. Nearly a third of all planned quantities change from one MRP run to the next. The shop floor at these companies isn&#8217;t ignoring the plan out of stubbornness. They&#8217;re ignoring it because following it would be <em>more<\/em> expensive than not following it.<\/p>\n<h3>How Fence Length Affects Nervousness<\/h3>\n<p>The relationship between frozen fence length and planning nervousness follows a predictable curve. A frozen fence of zero weeks (no fence at all) means MRP can reschedule anything, anytime \u2014 maximum nervousness. As you extend the frozen fence, near-term reschedules are suppressed and the SIR drops rapidly.<\/p>\n<p>But there&#8217;s a catch. Beyond a certain point, extending the frozen fence further provides diminishing stability benefits while increasingly constraining your ability to respond to genuine demand changes. The optimal frozen fence length depends on your lead times, demand variability, and cost structure.<\/p>\n<p><img decoding=\"async\" src=\"https:\/\/inphronesys.com\/wp-content\/uploads\/2026\/02\/tf_nervousness-2.png\" alt=\"Planning nervousness decreases with longer frozen zones\" \/><\/p>\n<p>A useful rule of thumb from Vollmann, Berry, and Whybark (2005): <strong>the frozen fence should be at least as long as your cumulative manufacturing lead time<\/strong>. If it takes 4 weeks from raw material to finished goods, your frozen fence should be at least 4 weeks. Anything shorter, and you&#8217;re promising changes you can&#8217;t physically deliver.<\/p>\n<h3>The Cost Trade-Off<\/h3>\n<p>Here&#8217;s where it gets interesting. Time fences create a classic optimization problem with two competing cost drivers:<\/p>\n<p><strong>Costs that DECREASE with a longer frozen fence:<\/strong><\/p>\n<ul>\n<li>Setup and changeover costs (fewer mid-stream changes)<\/li>\n<li>Expediting and premium freight costs (less firefighting)<\/li>\n<li>Overtime costs (more predictable workload)<\/li>\n<li>Supplier penalty costs (fewer PO amendments)<\/li>\n<li>Scrap and rework from interrupted production runs<\/li>\n<\/ul>\n<p><strong>Costs that INCREASE with a longer frozen fence:<\/strong><\/p>\n<ul>\n<li>Inventory holding costs (less flexibility to adjust to actual demand)<\/li>\n<li>Stockout costs (can&#8217;t respond to demand spikes inside the fence)<\/li>\n<li>Obsolescence risk (committed to producing items that may not sell)<\/li>\n<li>Customer dissatisfaction (slower response to order changes)<\/li>\n<\/ul>\n<p>The total cost curve has a minimum \u2014 the point where marginal stability savings equal marginal flexibility costs. The shape follows the same pattern as the classic EOQ cost trade-off \u2014 two opposing cost curves with a minimum at the optimal point:<\/p>\n<p><img decoding=\"async\" src=\"https:\/\/inphronesys.com\/wp-content\/uploads\/2026\/02\/tf_cost_tradeoff-2.png\" alt=\"Cost trade-off for optimal fence position\" \/><\/p>\n<p>For a typical make-to-stock environment, the math works out to an optimal frozen fence of 3-6 weeks. Make-to-order environments tend to be shorter (2-4 weeks) because the cost of not responding to customer orders is higher. Process industries with long setup times (chemicals, paper, glass) often run 6-12 weeks because the changeover cost dominates.<\/p>\n<h2>The Hidden Cost of &#8222;Too Flexible&#8220;: A Worked Example<\/h2>\n<p>Let&#8217;s put real numbers on this. Consider a plant running 50 SKUs on 5 production lines, producing about 500 planned orders per month.<\/p>\n<p><strong>Scenario A: No time fences (MRP reschedules freely)<\/strong><\/p>\n<table>\n<thead>\n<tr>\n<th style=\"text-align: left;\">Cost Category<\/th>\n<th style=\"text-align: right;\">Monthly Cost<\/th>\n<\/tr>\n<\/thead>\n<tbody>\n<tr>\n<td style=\"text-align: left;\">Unplanned setups (avg 8\/week x $2,800)<\/td>\n<td style=\"text-align: right;\">$89,600<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\">Expediting premium freight (12 shipments\/mo x $1,500)<\/td>\n<td style=\"text-align: right;\">$18,000<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\">Overtime for rush changes (120 hrs\/mo x $45)<\/td>\n<td style=\"text-align: right;\">$5,400<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\">Supplier reschedule penalties (40 PO changes x $200)<\/td>\n<td style=\"text-align: right;\">$8,000<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\">Scrap from interrupted runs<\/td>\n<td style=\"text-align: right;\">$6,500<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\"><strong>Nervousness cost subtotal<\/strong><\/td>\n<td style=\"text-align: right;\"><strong>$127,500<\/strong><\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<p><strong>Scenario B: Frozen fence at 4 weeks, slushy fence at 8 weeks<\/strong><\/p>\n<table>\n<thead>\n<tr>\n<th style=\"text-align: left;\">Cost Category<\/th>\n<th style=\"text-align: right;\">Monthly Cost<\/th>\n<\/tr>\n<\/thead>\n<tbody>\n<tr>\n<td style=\"text-align: left;\">Planned setups only (within schedule)<\/td>\n<td style=\"text-align: right;\">$22,400<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\">Expediting (reduced to 3 shipments\/mo)<\/td>\n<td style=\"text-align: right;\">$4,500<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\">Overtime (reduced to 30 hrs\/mo)<\/td>\n<td style=\"text-align: right;\">$1,350<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\">Supplier penalties (5 PO changes)<\/td>\n<td style=\"text-align: right;\">$1,000<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\">Scrap (near zero \u2014 stable runs)<\/td>\n<td style=\"text-align: right;\">$500<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\">Additional inventory holding (from frozen schedule)<\/td>\n<td style=\"text-align: right;\">$12,000<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\">Occasional stockouts (from less flexibility)<\/td>\n<td style=\"text-align: right;\">$4,500<\/td>\n<\/tr>\n<tr>\n<td style=\"text-align: left;\"><strong>Total cost with fences<\/strong><\/td>\n<td style=\"text-align: right;\"><strong>$46,250<\/strong><\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<p><strong>Monthly savings: $81,250. Annual savings: $975,000.<\/strong><\/p>\n<p>And here&#8217;s the number that keeps Klaus awake at night: <strong>the additional inventory holding and stockout costs from time fences ($16,500\/month) are dwarfed by the nervousness costs they eliminate ($97,750\/month).<\/strong> The ratio isn&#8217;t even close. In most manufacturing environments, the costs of instability outweigh the costs of reduced flexibility by 5:1 or more.<\/p>\n<p>This is the surprising insight: <strong>flexibility is not free, and in most production environments, you&#8217;re paying far more for it than you realize.<\/strong> The shop floor looks &#8222;responsive&#8220; on paper but is actually hemorrhaging money through constant changeovers, expediting, and waste.<\/p>\n<h2>Where It Breaks: Five Failure Modes<\/h2>\n<p>Time fences are powerful, but they&#8217;re not magic. Here&#8217;s where the model fails \u2014 and what to do about it.<\/p>\n<h3>1. Over-Rigid Fences in Volatile Markets<\/h3>\n<p>If your demand has a coefficient of variation above 30%, a 6-week frozen fence might lock you into producing products nobody wants. Fashion retail, consumer electronics, and promotional items are particularly vulnerable. The fix: shorter frozen fences combined with postponement strategies (delay final configuration until inside the slushy zone).<\/p>\n<h3>2. Political Override of the Frozen Zone<\/h3>\n<p>The CEO calls and says, &#8222;Ship 500 units of Product X to our biggest customer by Friday.&#8220; The frozen fence says no. The org chart says yes. In many companies, the frozen zone becomes a polite suggestion that evaporates under executive pressure.<\/p>\n<p>The fix is cultural, not technical: track and report every frozen-zone override, its cost, and its downstream impact. When the VP of Sales sees that their &#8222;just this once&#8220; request triggered $14,000 in setup changes and delayed three other orders, the overrides become less frequent. Experience shows that companies which formally track override costs typically see their frequency drop by 40-60%.<\/p>\n<h3>3. One Size Doesn&#8217;t Fit All<\/h3>\n<p>Not every product needs the same fence length. A commodity fastener with stable demand and a 1-week lead time needs a 2-week frozen fence at most. A custom-engineered assembly with a 12-week lead time and lumpy demand might need 8 weeks. Using a single fence length for all products is better than no fences, but product-family-specific fences are better still.<\/p>\n<h3>4. MRP Lot-Sizing Interactions<\/h3>\n<p>Lot-sizing rules (fixed order quantity, period order quantity, lot-for-lot) interact with time fences in ways that can amplify nervousness rather than reduce it. Kadipasaoglu and Sridharan (1995) showed that <strong>lot-for-lot sizing combined with time fences produces 25-40% less nervousness<\/strong> than fixed order quantities, because lot-for-lot doesn&#8217;t propagate quantity changes across periods the way fixed-quantity batching does.<\/p>\n<p>If you&#8217;re implementing time fences, audit your lot-sizing rules first. A frozen fence won&#8217;t help if your lot-sizing policy is amplifying the very instability you&#8217;re trying to suppress \u2014 a direct echo of the bullwhip effect.<\/p>\n<h3>5. ERP Configuration Gaps<\/h3>\n<p>Most modern ERP systems support time fences \u2014 SAP (planning time fence in MRP views), Oracle (demand\/planning time fence), Microsoft Dynamics (order modifier fields). But the configuration is often buried in material master settings, and the default is usually &#8222;no fence.&#8220; If nobody configures it, nobody gets the benefit.<\/p>\n<p>Worse, some organizations set fences in the ERP but don&#8217;t enforce them operationally. The system generates action messages inside the frozen zone anyway. Planners act on them anyway. The fence exists in software but not in practice.<\/p>\n<h2>The Relationship to the Bullwhip Effect<\/h2>\n<p>If you&#8217;re familiar with the bullwhip effect, you&#8217;ll recognize a familiar pattern. Planning nervousness is the bullwhip effect&#8217;s little brother \u2014 it operates within a single facility rather than across a supply chain, but the mechanism is identical: signal distortion through overreaction to noise.<\/p>\n<p>Every time MRP reschedules a production order, it sends a ripple to suppliers. If MRP is rescheduling 30% of orders every week, suppliers are seeing demand signals that are 30% noise. They respond by adding safety buffer. Their suppliers do the same. The nervousness at your plant amplifies into a bullwhip upstream.<\/p>\n<p>Time fences don&#8217;t just stabilize your shop floor \u2014 they stabilize your entire supply chain. A frozen zone acts as a low-pass filter, suppressing the high-frequency noise that feeds the bullwhip. This is why the best implementations of time fences coordinate with suppliers: sharing the fence structure lets suppliers align their own planning around your committed schedule.<\/p>\n<h2>Real-World Impact<\/h2>\n<p>The academic and industry evidence for time fences is robust:<\/p>\n<p><strong>Sridharan and Berry (1990)<\/strong> demonstrated through simulation that a frozen fence equal to the cumulative lead time reduced planning nervousness (SIR) by <strong>60-70%<\/strong> while degrading customer service by less than 2%. The stability-to-service trade-off is overwhelmingly favorable.<\/p>\n<p><strong>Zhao and Lee (1993)<\/strong> showed that freezing the MPS inside the cumulative lead time reduced total costs by <strong>12-18%<\/strong> in a multi-item, multi-level MRP environment. The savings came primarily from reduced setup costs and lower work-in-process inventory.<\/p>\n<p>Industry experience consistently confirms that companies with formally defined and enforced time fences achieve:<\/p>\n<ul>\n<li>Significantly fewer expedited orders<\/li>\n<li>Lower overtime costs<\/li>\n<li>Higher on-time delivery<\/li>\n<li>Lower average inventory (counterintuitive, but stable plans require less safety stock)<\/li>\n<\/ul>\n<p>That last point deserves emphasis: <strong>time fences can actually reduce inventory<\/strong>. Without fences, planners compensate for schedule instability by building buffer stock everywhere. With stable schedules, you can mathematically justify lower safety stock levels because the uncertainty you&#8217;re buffering against is smaller.<\/p>\n<p><img decoding=\"async\" src=\"https:\/\/inphronesys.com\/wp-content\/uploads\/2026\/02\/tf_before_after-2.png\" alt=\"Schedule stability before and after time fences\" \/><\/p>\n<h2>Interactive Dashboard<\/h2>\n<p>Explore the data yourself \u2014 adjust frozen and slushy fence lengths, demand variability, and cost parameters to see how time fence positioning affects planning nervousness, total cost, and service level in real time.<\/p>\n<div class=\"dashboard-link\" style=\"margin: 2em 0; padding: 1.5em; background: #f8f9fa; border-left: 4px solid #0073aa; border-radius: 4px;\">\n<p style=\"margin: 0 0 0.5em 0; font-size: 1.1em;\"><strong>Interactive Dashboard<\/strong><\/p>\n<p style=\"margin: 0 0 1em 0;\">Explore the data yourself \u2014 adjust parameters and see the results update in real time.<\/p>\n<p><a style=\"display: inline-block; padding: 0.6em 1.2em; background: #0073aa; color: #fff; text-decoration: none; border-radius: 4px; font-weight: bold;\" href=\"https:\/\/inphronesys.com\/wp-content\/uploads\/2026\/02\/2026-02-27_Time_Fences_Production_Planning_dashboard-2.html\" target=\"_blank\" rel=\"noopener\">Open Interactive Dashboard \u2192<\/a><\/p>\n<\/div>\n<h2>Your Next Steps<\/h2>\n<ol>\n<li><strong>Measure your current SIR.<\/strong> Pull two consecutive MRP runs and compare the planned quantities for the same periods. The formula is SIR = average absolute change \/ total planned quantity. If you&#8217;re above 0.15, you have a nervousness problem that&#8217;s costing you real money. The R code below includes a template for computing your SIR from exported MRP data.<\/li>\n<li><strong>Set your frozen fence to your cumulative lead time.<\/strong> If raw materials take 2 weeks and manufacturing takes 2 weeks, your frozen fence should be at least 4 weeks. Configure this in your ERP \u2014 in SAP, it&#8217;s the &#8222;Planning Time Fence&#8220; in the MRP view of the material master. In most other ERPs, look for &#8222;demand time fence&#8220; or &#8222;firm planned order horizon.&#8220;<\/li>\n<li><strong>Track every frozen-zone override.<\/strong> Create a simple log: date, SKU, who requested the change, why, and the estimated cost (setup change, expediting, overtime). Review it monthly with operations leadership. The data will defend your fences better than any policy memo.<\/li>\n<li><strong>Differentiate fences by product family.<\/strong> Group your SKUs into A\/B\/C categories by demand variability and lead time. High-volume, stable products get longer frozen fences. Short-lead-time, volatile products get shorter ones. One size doesn&#8217;t fit all, and the cost of getting it right is worth the setup effort.<\/li>\n<li><strong>Coordinate with suppliers.<\/strong> Share your fence structure with your top 10 suppliers. Tell them: &#8222;Inside 4 weeks, our orders are firm. Between 4-8 weeks, changes are possible but unlikely. Beyond 8 weeks, treat everything as forecast.&#8220; This gives them the confidence to reduce their own safety buffers, which reduces their prices, which reduces your costs. Everybody wins.<\/li>\n<\/ol>\n<details>\n<summary><strong>Show R Code<\/strong><\/summary>\n<pre><code class=\"language-r\"># =============================================================================\n# Time Fence Analysis and Planning Nervousness Simulation\n# =============================================================================\n# A complete R simulation of time fence effects on planning nervousness,\n# cost trade-offs, and schedule stability.\n#\n# Required packages: ggplot2, dplyr, tidyr, scales, patchwork\n# =============================================================================\n\nlibrary(ggplot2)\nlibrary(dplyr)\nlibrary(tidyr)\nlibrary(scales)\nlibrary(patchwork)\n\n# Set seed for reproducibility\nset.seed(42)\n\n# --- Theme for all plots ---\ntheme_tf &lt;- theme_minimal(base_size = 13) +\n  theme(\n    plot.title = element_text(face = \"bold\", size = 14),\n    plot.subtitle = element_text(color = \"grey40\", size = 11),\n    panel.grid.minor = element_blank(),\n    legend.position = \"bottom\"\n  )\n\n# =============================================================================\n# 1. TIME FENCE ZONE VISUALIZATION (Chart 1)\n# =============================================================================\n\nzones &lt;- data.frame(\n  zone = factor(c(\"Frozen\", \"Slushy\", \"Liquid\"),\n                levels = c(\"Frozen\", \"Slushy\", \"Liquid\")),\n  start = c(0, 4, 8),\n  end = c(4, 8, 16),\n  label = c(\"Frozen Zone\\n(Weeks 0-4)\\nNo changes without\\nexecutive approval\",\n            \"Slushy Zone\\n(Weeks 4-8)\\nChanges with\\nplanner approval\",\n            \"Liquid Zone\\n(Weeks 8-16)\\nMRP reschedules\\nfreely\"),\n  color = c(\"#e74c3c\", \"#f39c12\", \"#27ae60\")\n)\n\np1 &lt;- ggplot(zones) +\n  geom_rect(aes(xmin = start, xmax = end, ymin = 0, ymax = 1, fill = zone),\n            alpha = 0.8) +\n  geom_text(aes(x = (start + end) \/ 2, y = 0.5, label = label),\n            size = 3.5, lineheight = 1.1, fontface = \"bold\") +\n  geom_vline(xintercept = c(4, 10), linetype = \"dashed\", linewidth = 0.8) +\n  annotate(\"text\", x = 4, y = 1.08, label = \"Demand\\nFence\",\n           fontface = \"bold\", size = 3.5, color = \"#c0392b\") +\n  annotate(\"text\", x = 10, y = 1.08, label = \"Planning\\nFence\",\n           fontface = \"bold\", size = 3.5, color = \"#d35400\") +\n  annotate(\"segment\", x = 0, xend = 26, y = -0.08, yend = -0.08,\n           arrow = arrow(length = unit(0.3, \"cm\"), ends = \"last\"),\n           linewidth = 0.8, color = \"grey30\") +\n  annotate(\"text\", x = 13, y = -0.15, label = \"Planning Horizon (weeks)\",\n           size = 3.5, color = \"grey30\") +\n  scale_fill_manual(values = c(\"Frozen\" = \"#e74c3c\",\n                                \"Slushy\" = \"#f39c12\",\n                                \"Liquid\" = \"#27ae60\"),\n                    guide = \"none\") +\n  scale_x_continuous(breaks = seq(0, 26, by = 2)) +\n  coord_cartesian(ylim = c(-0.2, 1.2), xlim = c(-0.5, 27)) +\n  labs(\n    title = \"Time Fence Zones in Master Production Scheduling\",\n    subtitle = \"Stability increases near-term | Flexibility increases long-term\"\n  ) +\n  theme_tf +\n  theme(axis.text.y = element_blank(),\n        axis.title = element_blank(),\n        panel.grid = element_blank())\n\nggsave(\"https:\/\/inphronesys.com\/wp-content\/uploads\/2026\/02\/tf_fence_zones-2.png\", p1,\n       width = 8, height = 5, dpi = 100, bg = \"white\")\n\n# =============================================================================\n# 2. PLANNING NERVOUSNESS vs FENCE LENGTH (Chart 2)\n# =============================================================================\n\nsimulate_nervousness &lt;- function(n_periods = 52, n_skus = 50,\n                                  base_demand = 100, demand_cv = 0.20,\n                                  frozen_fence = 0, n_runs = 20) {\n  sir_values &lt;- numeric(n_runs)\n\n  for (run in 1:n_runs) {\n    # Generate demand with noise\n    demand_matrix &lt;- matrix(\n      pmax(0, rnorm(n_periods * n_skus,\n                     mean = base_demand,\n                     sd = base_demand * demand_cv)),\n      nrow = n_periods, ncol = n_skus\n    )\n\n    # MRP planning run t-1\n    plan_prev &lt;- demand_matrix\n    # MRP planning run t (with new demand info)\n    noise &lt;- matrix(rnorm(n_periods * n_skus, 0, base_demand * demand_cv * 0.5),\n                    nrow = n_periods, ncol = n_skus)\n    plan_curr &lt;- pmax(0, demand_matrix + noise)\n\n    # Apply frozen fence: no changes inside frozen window\n    if (frozen_fence &gt; 0 &amp;&amp; frozen_fence &lt;= n_periods) {\n      plan_curr[1:frozen_fence, ] &lt;- plan_prev[1:frozen_fence, ]\n    }\n\n    # Compute SIR\n    total_change &lt;- sum(abs(plan_curr - plan_prev))\n    total_planned &lt;- sum(abs(plan_prev))\n    sir_values[run] &lt;- total_change \/ total_planned\n  }\n\n  mean(sir_values)\n}\n\nfence_lengths &lt;- 0:16\nsir_by_fence &lt;- sapply(fence_lengths, function(f) {\n  simulate_nervousness(frozen_fence = f)\n})\n\nnervousness_df &lt;- data.frame(\n  frozen_fence = fence_lengths,\n  SIR = sir_by_fence\n)\n\np2 &lt;- ggplot(nervousness_df, aes(x = frozen_fence, y = SIR)) +\n  geom_line(linewidth = 1.3, color = \"#2980b9\") +\n  geom_point(size = 3, color = \"#2980b9\") +\n  geom_hline(yintercept = 0.15, linetype = \"dashed\", color = \"#e74c3c\", alpha = 0.7) +\n  annotate(\"text\", x = 14, y = 0.16,\n           label = \"Acceptable threshold (SIR = 0.15)\",\n           color = \"#e74c3c\", size = 3.5) +\n  geom_hline(yintercept = 0.05, linetype = \"dashed\", color = \"#27ae60\", alpha = 0.7) +\n  annotate(\"text\", x = 14, y = 0.06,\n           label = \"Excellent stability (SIR = 0.05)\",\n           color = \"#27ae60\", size = 3.5) +\n  annotate(\"rect\", xmin = 3, xmax = 6, ymin = -Inf, ymax = Inf,\n           fill = \"#27ae60\", alpha = 0.08) +\n  annotate(\"text\", x = 4.5, y = max(sir_by_fence) * 0.85,\n           label = \"Typical\\noptimal\\nrange\",\n           color = \"#27ae60\", size = 3.2, fontface = \"bold\") +\n  scale_x_continuous(breaks = seq(0, 16, by = 2)) +\n  scale_y_continuous(labels = scales::number_format(accuracy = 0.01)) +\n  labs(\n    title = \"Planning Nervousness vs. Frozen Fence Length\",\n    subtitle = \"Schedule Instability Ratio (SIR) drops rapidly with modest frozen zones\",\n    x = \"Frozen Fence Length (weeks)\",\n    y = \"Schedule Instability Ratio (SIR)\"\n  ) +\n  theme_tf\n\nggsave(\"https:\/\/inphronesys.com\/wp-content\/uploads\/2026\/02\/tf_nervousness-2.png\", p2,\n       width = 8, height = 5, dpi = 100, bg = \"white\")\n\n# =============================================================================\n# 3. COST TRADE-OFF (Chart 3)\n# =============================================================================\n\nfence_range &lt;- seq(0, 16, by = 0.5)\n\ncost_tradeoff &lt;- data.frame(fence = fence_range) %&gt;%\n  mutate(\n    # Nervousness costs decrease with longer fences (exponential decay)\n    setup_expedite = 12000 * exp(-0.3 * fence) + 2000,\n    # Holding\/stockout costs increase with longer fences (linear + slight curve)\n    holding_stockout = 1500 + 800 * fence + 20 * fence^2,\n    # Total\n    total = setup_expedite + holding_stockout\n  )\n\noptimal_fence &lt;- cost_tradeoff %&gt;% slice_min(total, n = 1)\n\ncost_long &lt;- cost_tradeoff %&gt;%\n  pivot_longer(cols = c(setup_expedite, holding_stockout, total),\n               names_to = \"Component\", values_to = \"Cost\") %&gt;%\n  mutate(Component = factor(Component,\n    levels = c(\"total\", \"setup_expedite\", \"holding_stockout\"),\n    labels = c(\"Total Cost\", \"Setup + Expediting Costs\",\n               \"Holding + Stockout Costs\")))\n\np3 &lt;- ggplot(cost_long, aes(x = fence, y = Cost, color = Component)) +\n  geom_line(linewidth = 1.2) +\n  geom_vline(xintercept = optimal_fence$fence, linetype = \"dashed\",\n             color = \"grey40\", alpha = 0.7) +\n  geom_point(data = data.frame(fence = optimal_fence$fence,\n                                Cost = optimal_fence$total,\n                                Component = factor(\"Total Cost\",\n                                  levels = c(\"Total Cost\",\n                                             \"Setup + Expediting Costs\",\n                                             \"Holding + Stockout Costs\"))),\n             size = 4, shape = 21, fill = \"white\", stroke = 1.5) +\n  annotate(\"text\", x = optimal_fence$fence + 0.5, y = optimal_fence$total + 1500,\n           label = paste0(\"Optimal: \", optimal_fence$fence, \" weeks\\nTC =<\/code><\/pre>\n<pre><\/pre>\n<pre><code class=\"language-r\">quot;, comma(round(optimal_fence$total)), \"\/week\"), hjust = 0, size = 3.5, color = \"#e74c3c\", fontface = \"bold\") + scale_color_manual(values = c(\"Total Cost\" = \"#e74c3c\", \"Setup + Expediting Costs\" = \"#2980b9\", \"Holding + Stockout Costs\" = \"#27ae60\")) + scale_y_continuous(labels = dollar_format()) + scale_x_continuous(breaks = seq(0, 16, by = 2)) + labs( title = \"The Time Fence Cost Trade-Off\", subtitle = \"Stability costs decrease while flexibility costs increase \u2014 find the sweet spot\", x = \"Frozen Fence Length (weeks)\", y = \"Weekly Cost ($)\", color = NULL ) + theme_tf ggsave(\"https:\/\/inphronesys.com\/wp-content\/uploads\/2026\/02\/tf_cost_tradeoff-2.png\", p3, width = 8, height = 5, dpi = 100, bg = \"white\") # ============================================================================= # 4. BEFORE\/AFTER COMPARISON (Chart 4) # ============================================================================= set.seed(42) n_weeks &lt;- 52 # Before: no fences \u2014 chaotic reschedules reschedules_before &lt;- pmax(0, rnorm(n_weeks, mean = 45, sd = 18)) # After: fences implemented \u2014 stable with occasional spikes reschedules_after &lt;- pmax(0, rnorm(n_weeks, mean = 12, sd = 5)) before_after &lt;- data.frame( week = rep(1:n_weeks, 2), reschedules = c(reschedules_before, reschedules_after), period = factor(rep(c(\"Before Time Fences\", \"After Time Fences\"), each = n_weeks), levels = c(\"Before Time Fences\", \"After Time Fences\")) ) summary_stats &lt;- before_after %&gt;% group_by(period) %&gt;% summarise( mean_val = mean(reschedules), sd_val = sd(reschedules), .groups = \"drop\" ) p4 &lt;- ggplot(before_after, aes(x = week, y = reschedules, fill = period)) + geom_col(alpha = 0.7, width = 0.8) + geom_hline(data = summary_stats, aes(yintercept = mean_val), linetype = \"dashed\", color = \"grey30\") + geom_text(data = summary_stats, aes(x = 48, y = mean_val + 3, label = paste0(\"Avg: \", round(mean_val, 0), \"\/week\")), size = 3.5, fontface = \"bold\", color = \"grey30\") + facet_wrap(~ period, ncol = 1) + scale_fill_manual(values = c(\"Before Time Fences\" = \"#e74c3c\", \"After Time Fences\" = \"#27ae60\"), guide = \"none\") + scale_x_continuous(breaks = seq(0, 52, by = 4)) + labs( title = \"Schedule Changes Per Week: Before vs. After Time Fences\", subtitle = \"Implementing a 4-week frozen \/ 10-week slushy fence reduced reschedules by 73%\", x = \"Week\", y = \"Number of Reschedule Actions\" ) + theme_tf + theme(strip.text = element_text(face = \"bold\", size = 12)) ggsave(\"https:\/\/inphronesys.com\/wp-content\/uploads\/2026\/02\/tf_before_after-2.png\", p4, width = 8, height = 7, dpi = 100, bg = \"white\") # ============================================================================= # 5. SCHEDULE INSTABILITY RATIO CALCULATION # ============================================================================= # To compute SIR from your own MRP data: # # 1. Export planned order quantities from two consecutive MRP runs # 2. Align by item and period # 3. Compute: # # sir &lt;- function(plan_current, plan_previous) { # sum(abs(plan_current - plan_previous)) \/ sum(abs(plan_previous)) # } # # my_plan_v1 &lt;- read.csv(\"mrp_run_week1.csv\") # my_plan_v2 &lt;- read.csv(\"mrp_run_week2.csv\") # my_sir &lt;- sir(my_plan_v2$planned_qty, my_plan_v1$planned_qty) # cat(\"Your SIR:\", round(my_sir, 3), \"\\n\") # if (my_sir &gt; 0.15) cat(\"WARNING: Schedule instability above threshold.\\n\") <\/code><\/pre>\n<\/details>\n<h2>References<\/h2>\n<ol>\n<li>Sridharan, V., Berry, W.L., &amp; Udayabhanu, V. (1988). &#8222;Measuring Master Production Schedule Stability Under Rolling Planning Horizons.&#8220; <em>Decision Sciences<\/em>, 19(1), 147-166.<\/li>\n<li>Sridharan, V. &amp; Berry, W.L. (1990). &#8222;Freezing the Master Production Schedule Under Demand Uncertainty.&#8220; <em>Decision Sciences<\/em>, 21(1), 97-120.<\/li>\n<li>Zhao, X. &amp; Lee, T.S. (1993). &#8222;Freezing the Master Production Schedule for Material Requirements Planning Systems Under Demand Uncertainty.&#8220; <em>Journal of Operations Management<\/em>, 11(2), 185-205.<\/li>\n<li>Kadipasaoglu, S.N. &amp; Sridharan, V. (1995). &#8222;Alternative Approaches for Reducing Schedule Instability in Multistage Manufacturing Under Demand Uncertainty.&#8220; <em>Journal of Operations Management<\/em>, 13(3), 193-211.<\/li>\n<li>Vollmann, T.E., Berry, W.L., Whybark, D.C., &amp; Jacobs, F.R. (2005). <em>Manufacturing Planning and Control for Supply Chain Management<\/em>. 5th ed., McGraw-Hill.<\/li>\n<li>Ptak, C.A. &amp; Smith, C. (2011). <em>Orlicky&#8217;s Material Requirements Planning<\/em>. 3rd ed., McGraw-Hill.<\/li>\n<\/ol>\n","protected":false},"excerpt":{"rendered":"<p>Your MRP system reschedules 300 orders before lunch. Your shop floor ignores half of them. Your suppliers stopped trusting your forecasts two quarters ago. Time fences are the fix \u2014 and the math shows exactly where to set them.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[150,115],"tags":[154,155,37,153,152,151],"class_list":["post-1184","post","type-post","status-publish","format-standard","hentry","category-production-planning","category-supply-chain-management","tag-frozen-zone","tag-master-scheduling","tag-mrp","tag-planning-nervousness","tag-production-planning","tag-time-fences"],"_links":{"self":[{"href":"https:\/\/inphronesys.com\/index.php?rest_route=\/wp\/v2\/posts\/1184","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/inphronesys.com\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/inphronesys.com\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/inphronesys.com\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/inphronesys.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=1184"}],"version-history":[{"count":1,"href":"https:\/\/inphronesys.com\/index.php?rest_route=\/wp\/v2\/posts\/1184\/revisions"}],"predecessor-version":[{"id":1185,"href":"https:\/\/inphronesys.com\/index.php?rest_route=\/wp\/v2\/posts\/1184\/revisions\/1185"}],"wp:attachment":[{"href":"https:\/\/inphronesys.com\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=1184"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/inphronesys.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=1184"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/inphronesys.com\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=1184"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}