{
  "id": 418287,
  "title": "3rd Place - Predict Multipliers with GRU",
  "content": "<p>Thank you Kaggle and GoDaddy for an exciting forecasting competition!</p>\n<h1>Predict Multipliers with TensorFlow GRU</h1>\n<p>Our forecasting models need to predict 3135 county microbusiness density predictions per future month. The public LB is one future month and the private LB is three future months (with 2 month gap between train and test).</p>\n<p>From Kaggle's M5 competition <a href=\"https://www.kaggle.com/competitions/m5-forecasting-accuracy/discussion/163621\" target=\"_blank\">here</a> we learned that predicting multipliers (between the test time period and train time period) was most important. For example in M5, we could take an average public notebook and multiply all predictions by <code>0.95</code> and win Gold medal !! Similarly in Kaggle's GoDaddy competition, a simple last value baseline multiplied by the correct January/December multiplier of <code>1.0045</code> as shown in Vitaly's notebook <a href=\"https://www.kaggle.com/code/vitalykudelya/21-lines-of-code\" target=\"_blank\">here</a> achieved Gold medal public LB for many months!</p>\n<p>To predict multipliers, we convert train data into multipliers and then train a TensorFlow GRU. This simple model achieves 15th place Gold. Then if we post process the multipliers based on ratios learned from LB probing, we boost our solution to 3rd place Gold !!</p>\n<h1>Original Train Data</h1>\n<p>Kaggle gave us 41 historical months of data for each of 3135 USA counties. </p>\n<p><img src=\"https://raw.githubusercontent.com/cdeotte/Kaggle_Images/main/Jun-2023/data1.png\" alt=\"\"></p>\n<h1>Step 1 - Adjust Train Data</h1>\n<p>The definition of microbusiness density is <code>micro businesses per 100 people over age 18</code>. The value of microbusiness density changes when county population changes. So the first step is to convert all microbusiness density to use the same 2021 census. We use the formula</p>\n<pre><code> = microbusiness_density * (population / population_year_2021)\n</code></pre>\n<h1>Step 2 - Create 56,000 Time Series!</h1>\n<p>For each county, we create 18 time series. We use 13 consecutive months to train our GRU and predict the next 5 months. (Pictured below is only 3 time series per county for illustration purposes). Afterward, we have 56,000 time series to train with!</p>\n<p><img src=\"https://raw.githubusercontent.com/cdeotte/Kaggle_Images/main/Jun-2023/data2.png\" alt=\"\"></p>\n<h1>Step 3 - Use Only Top 90% Largest Counties</h1>\n<p>We notice that the smallest 10% counties have nearly the same microbusiness density from month to month, so we only train our GRU using the largest 90% counties. During inference, we will use the last known value as prediction for small counties.</p>\n<p><img src=\"https://raw.githubusercontent.com/cdeotte/Kaggle_Images/main/Mar-2023/growth.png\" alt=\"\"></p>\n<h1>Step 4 - Convert to Multipliers</h1>\n<p>Each county has 13 months of train and 5 months of valid. We will convert the raw micro business data into ratios by replacing each value with the ratio of current month divided by previous month. Afterward we will have 12 months of train ratios and 5 months of valid ratios</p>\n<pre><code>\n k in range():\n    [:,k+] = old_data[:,k+] / old_data[:,k]\n</code></pre>\n<h1>Step 5 - Train GRU with GroupKFold</h1>\n<p>When creating KFold we need to use GroupKFold and keep all time series for each county (from the possible 18 time series per each county) within the same fold. Otherwise CV score will be inaccurate and we cannot optimize our models hyperparameters correctly. Below is our TensorFlow GRU model which takes an input of 12 ratios and predicts 5 ratios:</p>\n<pre><code>def build_model():\n\n    inp = tf.keras.Input(shape=(12,1)) # INPUT SHAPE IS 12\n    x = tf.keras.layers.GRU(=8, =)(inp)\n    x = tf.keras.layers.GRU(=8, =)(x)\n    x = tf.keras.layers.GRU(=8, =)(x)\n    x = tf.keras.layers.Dense(5,=)(x) # OUTPUT SHAPE IS 5\n    model = tf.keras.Model(=inp, =x)\n\n    opt = tf.keras.optimizers.Adam(=1e-4)\n    loss = tf.keras.losses.MeanSquaredError()\n    model.compile(=loss, optimizer = opt)\n\n    return model\n</code></pre>\n<h1>Step 6 - Infer and Post Process</h1>\n<p>We predict each county individually. To make predictions for January 2023. We begin with the last known value (of the county we are predicting) from December 2022 and multiply by the first ratio predicted by our model. To predict Feb 2023, we take our Jan 2023 prediction and multiply by the second ratio predicted by our model. To predict Mar 2023, we multiply Feb 2023 by third ratio. To predict Apr 2023, we multiply by fourth ratio. And finally to predict May 2023, we multiply by fifth ratio.</p>\n<p>We can improve our predictions by modifying the first ratio (which is the ratio of January 2023 divided by December 2022) by information from probing the public LB.  Probing informs us that the best January/December average ratio for the largest 90% counties is <code>1.0045</code>. Similarly, we can improve our predictions for small counties by probing the public LB to find ratios for different sized small counties.</p>\n<p>Post process boosts our GRU solution from 12th place Gold to 3rd place Gold !!</p>\n<h1>GRU Solution Code Published</h1>\n<p>Full solution code with preprocess, train, and infer is published <a href=\"https://www.kaggle.com/code/cdeotte/gru-model-3rd-place-gold\" target=\"_blank\">here</a>. </p>\n<h1>More Solution Models</h1>\n<p>My final two submissions were</p>\n<ul>\n<li>GRU with PP - 3rd place</li>\n<li>Linear Model with PP - 10th place</li>\n</ul>\n<p>More information about my linear model is <a href=\"https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/395098\" target=\"_blank\">here</a>. Enjoy!</p>",
  "comments": [
    {
      "id": 2312688,
      "author_name": "Deniz",
      "author_url": "",
      "post_date": "2023-06-22T06:03:40.610000",
      "content": "<p>Congrats Chris and thanks for sharing.</p>\n<p>I've also tried GRU over all dataset, rather than 90 %,  also my <a href=\"https://github.com/denizstij/GoDaddy_Microbusiness_Density_Forecasting/blob/main/recurrent-gru-nn-godaddy-mbd-forecasting.ipynb\" target=\"_blank\">GRU </a> was wider it seems. And it seems my solution is over complicated compare to yours. </p>\n<p>In my final solution, i selected another solution, so now i cannot see  final result for my GRU solution. </p>\n<p>Thanks again for sharing. </p>\n<p>By the way, why do we have to explicitly multiply the result? should not GRU find out this relation and apply?<br>\nrather than multiplying, If we had used stacking (where final model is a linear regression), would that automatically add multiplying factor?</p>",
      "votes": 1,
      "replies": [
        {
          "id": 2312697,
          "author_name": "Chris Deotte",
          "author_url": "",
          "post_date": "2023-06-22T06:11:09.777000",
          "content": "<p>The competition metric is SMAPE which is about ratios of error divided by mean of prediction and ground truth. When training a model, using different losses can have different effects on model accuracy with relation to competition metric. Another way to affect model accuracy without changing the loss function is to transform the targets. Using MSE loss with ratios does a better job optimizing SMAPE than trying to predict the raw microbusiness values with another loss. Also transforming targets make more targets similar. For example when using raw microbusiness values, maybe the values do not repeat themselves often, but when converting everything into ratios, the ratios do repeat themselves often which reinforce the model's learning.</p>",
          "votes": 2,
          "replies": []
        }
      ]
    },
    {
      "id": 2312022,
      "author_name": "Pooja Chauhan",
      "author_url": "",
      "post_date": "2023-06-21T15:57:55.940000",
      "content": "<p>Impressive 3rd place solution using TensorFlow GRU to predict multipliers in forecasting microbusiness density. Adjusted train data using population ratios. Created 56,000 time series for training. Focused on top 90% largest counties and used last known value for small counties. Trained GRU model with GroupKFold and post-processed predictions. Achieved 3rd place Gold. Well done!</p>",
      "votes": 1,
      "replies": []
    },
    {
      "id": 2311574,
      "author_name": "janedangrj",
      "author_url": "",
      "post_date": "2023-06-21T08:45:55.210000",
      "content": "<p>Thanks for sharing. Congratulations Chris!</p>",
      "votes": 1,
      "replies": []
    },
    {
      "id": 2311544,
      "author_name": "Akshit Sharma",
      "author_url": "",
      "post_date": "2023-06-21T08:27:12.997000",
      "content": "<p>Congratulations! &amp; Thanks a lot for sharing this <a href=\"https://www.kaggle.com/cdeotte\" target=\"_blank\">@cdeotte</a> </p>",
      "votes": 1,
      "replies": []
    },
    {
      "id": 2311543,
      "author_name": "Darek Kłeczek",
      "author_url": "",
      "post_date": "2023-06-21T08:27:09.993000",
      "content": "<p>Thanks for sharing Chris, great lesson in how to approach time series forecasting!</p>",
      "votes": 1,
      "replies": []
    },
    {
      "id": 2311365,
      "author_name": "Serigne ",
      "author_url": "",
      "post_date": "2023-06-21T06:12:49.680000",
      "content": "<p>Congrats Chris <br>\nAlways coming with very insightful solutions and write-ups </p>",
      "votes": 1,
      "replies": []
    },
    {
      "id": 2310740,
      "author_name": "FL94",
      "author_url": "",
      "post_date": "2023-06-20T15:21:50.717000",
      "content": "<p>Thanks for sharing, very instructive and concise :)</p>",
      "votes": 1,
      "replies": []
    },
    {
      "id": 2310515,
      "author_name": "Yijie Xu",
      "author_url": "",
      "post_date": "2023-06-20T12:28:15.673000",
      "content": "<p>Great explanation, and a very interesting approach - 56K time series wasn't something that came to mind at all!</p>",
      "votes": 1,
      "replies": []
    },
    {
      "id": 2310011,
      "author_name": "CoreyJamesLevinson",
      "author_url": "",
      "post_date": "2023-06-20T03:59:42.077000",
      "content": "<p>Great job Chris, thank you for sharing. Congrats on 3rd place!</p>",
      "votes": 1,
      "replies": []
    },
    {
      "id": 2309902,
      "author_name": "@kaggleqrdl",
      "author_url": "",
      "post_date": "2023-06-20T01:08:26.637000",
      "content": "<p>You know you want to - <a href=\"https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/418308\" target=\"_blank\">https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/418308</a></p>\n<p>:)</p>",
      "votes": 1,
      "replies": []
    },
    {
      "id": 2309719,
      "author_name": "@kaggleqrdl",
      "author_url": "",
      "post_date": "2023-06-19T20:46:27.380000",
      "content": "<p>Great job chris.  q:  Did you delete your previous leaderboard post on this?  I couldn't find it and was curious about the diff.</p>",
      "votes": 1,
      "replies": [
        {
          "id": 2309721,
          "author_name": "Chris Deotte",
          "author_url": "",
          "post_date": "2023-06-19T20:48:37.717000",
          "content": "<p>No, my previous post is <a href=\"https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/395098\" target=\"_blank\">here</a></p>",
          "votes": 1,
          "replies": []
        },
        {
          "id": 2309723,
          "author_name": "Chris Deotte",
          "author_url": "",
          "post_date": "2023-06-19T20:50:44.243000",
          "content": "<p>Congratulations <a href=\"https://www.kaggle.com/kaggleqrdl\" target=\"_blank\">@kaggleqrdl</a> winning first place!</p>",
          "votes": 1,
          "replies": []
        }
      ]
    },
    {
      "id": 2315140,
      "author_name": "TAK",
      "author_url": "",
      "post_date": "2023-06-23T20:54:25.067000",
      "content": "<p>Congratulations, Chris! Thank you so much for sharing. I have learned some great eye-opening points from this. It helps guide me in looking back at my code again.</p>",
      "votes": 2,
      "replies": []
    },
    {
      "id": 2311561,
      "author_name": "Yu Wu",
      "author_url": "",
      "post_date": "2023-06-21T08:37:08.057000",
      "content": "<p>Ty Chris, your post is always impressive and insightful</p>",
      "votes": 2,
      "replies": []
    },
    {
      "id": 2311494,
      "author_name": "Raheem Nasirudeen",
      "author_url": "",
      "post_date": "2023-06-21T07:32:58.220000",
      "content": "<p>A big congratulations, I am so happy you win this ❤️ </p>",
      "votes": 2,
      "replies": []
    },
    {
      "id": 2309942,
      "author_name": "Jaewook Kim",
      "author_url": "",
      "post_date": "2023-06-20T02:25:20.063000",
      "content": "<p>Congratulations <a href=\"https://www.kaggle.com/cdeotte\" target=\"_blank\">@cdeotte</a> and <a href=\"https://www.kaggle.com/kaggleqrdl\" target=\"_blank\">@kaggleqrdl</a> 🎉<br>\nThank for your kind explanation. I have some questions.  </p>\n<ol>\n<li>How is the 1.0045 value obtained through probing used? When predicting 5 values, is it fixed as the first ratio value?</li>\n<li>Will the remaining 10% counties initially have 5 multipliers becoming 1?</li>\n<li>After probing for the remaining 10% counties, will only the first multiplier change to the explored value?</li>\n</ol>",
      "votes": 2,
      "replies": [
        {
          "id": 2310047,
          "author_name": "Chris Deotte",
          "author_url": "",
          "post_date": "2023-06-20T04:52:03.593000",
          "content": "<blockquote>\n  <p>How is the 1.0045 value obtained through probing used? When predicting 5 values, is it fixed as the first ratio value?</p>\n</blockquote>\n<p>After the GRU makes prediction for January, we compute the ratio of \"average January prediction\" divided by \"average December prediction\" for large counties. The result is  <code>1.0032</code>. This is not the optimal ratio. So we multiply every January prediction for large counties by <code>1.0012</code>. Afterward, the the ratio of \"average January prediction\" divided by \"average December prediction\" is <code>1.0045</code> and our public LB and private LB are boosted.</p>\n<p>Regarding the small counties, each begins with multiplier of <code>1</code> which means that each small county prediction uses the December 2022 value. We then try different multipliers for different small counties and keep ones that improve LB. Basically we are finding what the small counties ground truth is for January 2023. Then our final submission uses the January values for small counties instead of December values for small counties. This boosts public and private LB.</p>\n<p>Both post processes combined improve CV and LB by about <code>+0.05</code></p>",
          "votes": 3,
          "replies": [
            {
              "id": 2318233,
              "author_name": "Alexander Suen",
              "author_url": "",
              "post_date": "2023-06-26T08:50:26.033000",
              "content": "<p>Congrats! May I ask what is \"average December prediction\"? Is it predict by the 1st multiplier multiply Nov's MD?</p>",
              "votes": 0,
              "replies": []
            }
          ]
        }
      ]
    },
    {
      "id": 2375531,
      "author_name": "Abin Singh",
      "author_url": "",
      "post_date": "2023-08-05T17:43:19.343000",
      "content": "<p>Congratulations Chris. Thank you so much for sharing. </p>",
      "votes": 0,
      "replies": []
    },
    {
      "id": 2321040,
      "author_name": "LIXishere",
      "author_url": "",
      "post_date": "2023-06-28T08:37:07.310000",
      "content": "<p>hi Chris！Most people (including me) predict the rate of change (i.e. multiplier) or growth rate, while few people directly predict the density of enterprises. However, I am only because the former performs better in various verifications and results. Can there be some explanation from a theoretical perspective? Looking forward to your reply!</p>",
      "votes": 0,
      "replies": []
    },
    {
      "id": 2318429,
      "author_name": "justin1357",
      "author_url": "",
      "post_date": "2023-06-26T11:10:49.527000",
      "content": "<p><strong>multiplier</strong>,Simple but wonderful!!!</p>",
      "votes": 0,
      "replies": []
    },
    {
      "id": 2317205,
      "author_name": "ls",
      "author_url": "",
      "post_date": "2023-06-25T14:03:07.080000",
      "content": "<p>Congrats and thanks for sharing.</p>",
      "votes": 1,
      "replies": []
    },
    {
      "id": 2310831,
      "author_name": "MhatGPT",
      "author_url": "",
      "post_date": "2023-06-20T16:24:10.607000",
      "content": "<p>Thanks for posting!</p>",
      "votes": 2,
      "replies": []
    },
    {
      "id": 2310691,
      "author_name": "dragon zhang",
      "author_url": "",
      "post_date": "2023-06-20T14:49:21.990000",
      "content": "<p>thanks for sharing!</p>",
      "votes": 2,
      "replies": []
    },
    {
      "id": 2315690,
      "author_name": "",
      "author_url": "",
      "post_date": "2023-06-24T10:20:31.407000",
      "content": "<p>Thanks for sharing. Congrats!</p>",
      "votes": 2,
      "replies": []
    }
  ],
  "comment_count": 27,
  "messages": [
    {
      "id": 2309715,
      "postDate": "2023-06-19T20:38:42.060Z",
      "content": "<p>Thank you Kaggle and GoDaddy for an exciting forecasting competition!</p>\n<h1>Predict Multipliers with TensorFlow GRU</h1>\n<p>Our forecasting models need to predict 3135 county microbusiness density predictions per future month. The public LB is one future month and the private LB is three future months (with 2 month gap between train and test).</p>\n<p>From Kaggle's M5 competition <a href=\"https://www.kaggle.com/competitions/m5-forecasting-accuracy/discussion/163621\" target=\"_blank\">here</a> we learned that predicting multipliers (between the test time period and train time period) was most important. For example in M5, we could take an average public notebook and multiply all predictions by <code>0.95</code> and win Gold medal !! Similarly in Kaggle's GoDaddy competition, a simple last value baseline multiplied by the correct January/December multiplier of <code>1.0045</code> as shown in Vitaly's notebook <a href=\"https://www.kaggle.com/code/vitalykudelya/21-lines-of-code\" target=\"_blank\">here</a> achieved Gold medal public LB for many months!</p>\n<p>To predict multipliers, we convert train data into multipliers and then train a TensorFlow GRU. This simple model achieves 15th place Gold. Then if we post process the multipliers based on ratios learned from LB probing, we boost our solution to 3rd place Gold !!</p>\n<h1>Original Train Data</h1>\n<p>Kaggle gave us 41 historical months of data for each of 3135 USA counties. </p>\n<p><img src=\"https://raw.githubusercontent.com/cdeotte/Kaggle_Images/main/Jun-2023/data1.png\" alt=\"\"></p>\n<h1>Step 1 - Adjust Train Data</h1>\n<p>The definition of microbusiness density is <code>micro businesses per 100 people over age 18</code>. The value of microbusiness density changes when county population changes. So the first step is to convert all microbusiness density to use the same 2021 census. We use the formula</p>\n<pre><code> = microbusiness_density * (population / population_year_2021)\n</code></pre>\n<h1>Step 2 - Create 56,000 Time Series!</h1>\n<p>For each county, we create 18 time series. We use 13 consecutive months to train our GRU and predict the next 5 months. (Pictured below is only 3 time series per county for illustration purposes). Afterward, we have 56,000 time series to train with!</p>\n<p><img src=\"https://raw.githubusercontent.com/cdeotte/Kaggle_Images/main/Jun-2023/data2.png\" alt=\"\"></p>\n<h1>Step 3 - Use Only Top 90% Largest Counties</h1>\n<p>We notice that the smallest 10% counties have nearly the same microbusiness density from month to month, so we only train our GRU using the largest 90% counties. During inference, we will use the last known value as prediction for small counties.</p>\n<p><img src=\"https://raw.githubusercontent.com/cdeotte/Kaggle_Images/main/Mar-2023/growth.png\" alt=\"\"></p>\n<h1>Step 4 - Convert to Multipliers</h1>\n<p>Each county has 13 months of train and 5 months of valid. We will convert the raw micro business data into ratios by replacing each value with the ratio of current month divided by previous month. Afterward we will have 12 months of train ratios and 5 months of valid ratios</p>\n<pre><code>\n k in range():\n    [:,k+] = old_data[:,k+] / old_data[:,k]\n</code></pre>\n<h1>Step 5 - Train GRU with GroupKFold</h1>\n<p>When creating KFold we need to use GroupKFold and keep all time series for each county (from the possible 18 time series per each county) within the same fold. Otherwise CV score will be inaccurate and we cannot optimize our models hyperparameters correctly. Below is our TensorFlow GRU model which takes an input of 12 ratios and predicts 5 ratios:</p>\n<pre><code>def build_model():\n\n    inp = tf.keras.Input(shape=(12,1)) # INPUT SHAPE IS 12\n    x = tf.keras.layers.GRU(=8, =)(inp)\n    x = tf.keras.layers.GRU(=8, =)(x)\n    x = tf.keras.layers.GRU(=8, =)(x)\n    x = tf.keras.layers.Dense(5,=)(x) # OUTPUT SHAPE IS 5\n    model = tf.keras.Model(=inp, =x)\n\n    opt = tf.keras.optimizers.Adam(=1e-4)\n    loss = tf.keras.losses.MeanSquaredError()\n    model.compile(=loss, optimizer = opt)\n\n    return model\n</code></pre>\n<h1>Step 6 - Infer and Post Process</h1>\n<p>We predict each county individually. To make predictions for January 2023. We begin with the last known value (of the county we are predicting) from December 2022 and multiply by the first ratio predicted by our model. To predict Feb 2023, we take our Jan 2023 prediction and multiply by the second ratio predicted by our model. To predict Mar 2023, we multiply Feb 2023 by third ratio. To predict Apr 2023, we multiply by fourth ratio. And finally to predict May 2023, we multiply by fifth ratio.</p>\n<p>We can improve our predictions by modifying the first ratio (which is the ratio of January 2023 divided by December 2022) by information from probing the public LB.  Probing informs us that the best January/December average ratio for the largest 90% counties is <code>1.0045</code>. Similarly, we can improve our predictions for small counties by probing the public LB to find ratios for different sized small counties.</p>\n<p>Post process boosts our GRU solution from 12th place Gold to 3rd place Gold !!</p>\n<h1>GRU Solution Code Published</h1>\n<p>Full solution code with preprocess, train, and infer is published <a href=\"https://www.kaggle.com/code/cdeotte/gru-model-3rd-place-gold\" target=\"_blank\">here</a>. </p>\n<h1>More Solution Models</h1>\n<p>My final two submissions were</p>\n<ul>\n<li>GRU with PP - 3rd place</li>\n<li>Linear Model with PP - 10th place</li>\n</ul>\n<p>More information about my linear model is <a href=\"https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/395098\" target=\"_blank\">here</a>. Enjoy!</p>",
      "rawMarkdown": "Thank you Kaggle and GoDaddy for an exciting forecasting competition!\n\n# Predict Multipliers with TensorFlow GRU\nOur forecasting models need to predict 3135 county microbusiness density predictions per future month. The public LB is one future month and the private LB is three future months (with 2 month gap between train and test).\n\nFrom Kaggle's M5 competition [here][1] we learned that predicting multipliers (between the test time period and train time period) was most important. For example in M5, we could take an average public notebook and multiply all predictions by `0.95` and win Gold medal !! Similarly in Kaggle's GoDaddy competition, a simple last value baseline multiplied by the correct January/December multiplier of `1.0045` as shown in Vitaly's notebook [here][2] achieved Gold medal public LB for many months!\n\nTo predict multipliers, we convert train data into multipliers and then train a TensorFlow GRU. This simple model achieves 15th place Gold. Then if we post process the multipliers based on ratios learned from LB probing, we boost our solution to 3rd place Gold !!\n\n# Original Train Data\nKaggle gave us 41 historical months of data for each of 3135 USA counties. \n\n![](https://raw.githubusercontent.com/cdeotte/Kaggle_Images/main/Jun-2023/data1.png)\n\n# Step 1 - Adjust Train Data\n\nThe definition of microbusiness density is `micro businesses per 100 people over age 18`. The value of microbusiness density changes when county population changes. So the first step is to convert all microbusiness density to use the same 2021 census. We use the formula\n\n    adjusted_microbusiness_density = microbusiness_density * (population / population_year_2021)\n\n# Step 2 - Create 56,000 Time Series!\nFor each county, we create 18 time series. We use 13 consecutive months to train our GRU and predict the next 5 months. (Pictured below is only 3 time series per county for illustration purposes). Afterward, we have 56,000 time series to train with!\n\n![](https://raw.githubusercontent.com/cdeotte/Kaggle_Images/main/Jun-2023/data2.png)\n\n# Step 3 - Use Only Top 90% Largest Counties\nWe notice that the smallest 10% counties have nearly the same microbusiness density from month to month, so we only train our GRU using the largest 90% counties. During inference, we will use the last known value as prediction for small counties.\n\n![](https://raw.githubusercontent.com/cdeotte/Kaggle_Images/main/Mar-2023/growth.png)\n\n# Step 4 - Convert to Multipliers\nEach county has 13 months of train and 5 months of valid. We will convert the raw micro business data into ratios by replacing each value with the ratio of current month divided by previous month. Afterward we will have 12 months of train ratios and 5 months of valid ratios\n\n    # CONVERT TO RATIOS\n    for k in range(17):\n        new_data[:,k+1] = old_data[:,k+1] / old_data[:,k]\n\n# Step 5 - Train GRU with GroupKFold\nWhen creating KFold we need to use GroupKFold and keep all time series for each county (from the possible 18 time series per each county) within the same fold. Otherwise CV score will be inaccurate and we cannot optimize our models hyperparameters correctly. Below is our TensorFlow GRU model which takes an input of 12 ratios and predicts 5 ratios:\n\n    def build_model():\n    \n        inp = tf.keras.Input(shape=(12,1)) # INPUT SHAPE IS 12\n        x = tf.keras.layers.GRU(units=8, return_sequences=True)(inp)\n        x = tf.keras.layers.GRU(units=8, return_sequences=True)(x)\n        x = tf.keras.layers.GRU(units=8, return_sequences=False)(x)\n        x = tf.keras.layers.Dense(5,activation='linear')(x) # OUTPUT SHAPE IS 5\n        model = tf.keras.Model(inputs=inp, outputs=x)\n    \n        opt = tf.keras.optimizers.Adam(learning_rate=1e-4)\n        loss = tf.keras.losses.MeanSquaredError()\n        model.compile(loss=loss, optimizer = opt)\n    \n        return model\n\n# Step 6 - Infer and Post Process\nWe predict each county individually. To make predictions for January 2023. We begin with the last known value (of the county we are predicting) from December 2022 and multiply by the first ratio predicted by our model. To predict Feb 2023, we take our Jan 2023 prediction and multiply by the second ratio predicted by our model. To predict Mar 2023, we multiply Feb 2023 by third ratio. To predict Apr 2023, we multiply by fourth ratio. And finally to predict May 2023, we multiply by fifth ratio.\n\nWe can improve our predictions by modifying the first ratio (which is the ratio of January 2023 divided by December 2022) by information from probing the public LB.  Probing informs us that the best January/December average ratio for the largest 90% counties is `1.0045`. Similarly, we can improve our predictions for small counties by probing the public LB to find ratios for different sized small counties.\n\nPost process boosts our GRU solution from 12th place Gold to 3rd place Gold !!\n\n# GRU Solution Code Published\nFull solution code with preprocess, train, and infer is published [here][3]. \n\n# More Solution Models\nMy final two submissions were\n* GRU with PP - 3rd place\n* Linear Model with PP - 10th place\n\nMore information about my linear model is [here][4]. Enjoy!\n\n[1]: https://www.kaggle.com/competitions/m5-forecasting-accuracy/discussion/163621\n[2]: https://www.kaggle.com/code/vitalykudelya/21-lines-of-code\n[3]: https://www.kaggle.com/code/cdeotte/gru-model-3rd-place-gold\n[4]: https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/395098",
      "votes": 83
    },
    {
      "id": 2312688,
      "postDate": "2023-06-22T06:03:40.610Z",
      "content": "<p>Congrats Chris and thanks for sharing.</p>\n<p>I've also tried GRU over all dataset, rather than 90 %,  also my <a href=\"https://github.com/denizstij/GoDaddy_Microbusiness_Density_Forecasting/blob/main/recurrent-gru-nn-godaddy-mbd-forecasting.ipynb\" target=\"_blank\">GRU </a> was wider it seems. And it seems my solution is over complicated compare to yours. </p>\n<p>In my final solution, i selected another solution, so now i cannot see  final result for my GRU solution. </p>\n<p>Thanks again for sharing. </p>\n<p>By the way, why do we have to explicitly multiply the result? should not GRU find out this relation and apply?<br>\nrather than multiplying, If we had used stacking (where final model is a linear regression), would that automatically add multiplying factor?</p>",
      "rawMarkdown": "Congrats Chris and thanks for sharing.\n\nI've also tried GRU over all dataset, rather than 90 %,  also my [GRU ](https://github.com/denizstij/GoDaddy_Microbusiness_Density_Forecasting/blob/main/recurrent-gru-nn-godaddy-mbd-forecasting.ipynb) was wider it seems. And it seems my solution is over complicated compare to yours. \n\nIn my final solution, i selected another solution, so now i cannot see  final result for my GRU solution. \n\nThanks again for sharing. \n\nBy the way, why do we have to explicitly multiply the result? should not GRU find out this relation and apply?\nrather than multiplying, If we had used stacking (where final model is a linear regression), would that automatically add multiplying factor?\n",
      "votes": 1,
      "replies": [
        {
          "id": 2312697,
          "postDate": "2023-06-22T06:11:09.777Z",
          "content": "<p>The competition metric is SMAPE which is about ratios of error divided by mean of prediction and ground truth. When training a model, using different losses can have different effects on model accuracy with relation to competition metric. Another way to affect model accuracy without changing the loss function is to transform the targets. Using MSE loss with ratios does a better job optimizing SMAPE than trying to predict the raw microbusiness values with another loss. Also transforming targets make more targets similar. For example when using raw microbusiness values, maybe the values do not repeat themselves often, but when converting everything into ratios, the ratios do repeat themselves often which reinforce the model's learning.</p>",
          "rawMarkdown": "The competition metric is SMAPE which is about ratios of error divided by mean of prediction and ground truth. When training a model, using different losses can have different effects on model accuracy with relation to competition metric. Another way to affect model accuracy without changing the loss function is to transform the targets. Using MSE loss with ratios does a better job optimizing SMAPE than trying to predict the raw microbusiness values with another loss. Also transforming targets make more targets similar. For example when using raw microbusiness values, maybe the values do not repeat themselves often, but when converting everything into ratios, the ratios do repeat themselves often which reinforce the model's learning.",
          "votes": 2
        }
      ]
    },
    {
      "id": 2312022,
      "postDate": "2023-06-21T15:57:55.940Z",
      "content": "<p>Impressive 3rd place solution using TensorFlow GRU to predict multipliers in forecasting microbusiness density. Adjusted train data using population ratios. Created 56,000 time series for training. Focused on top 90% largest counties and used last known value for small counties. Trained GRU model with GroupKFold and post-processed predictions. Achieved 3rd place Gold. Well done!</p>",
      "rawMarkdown": "Impressive 3rd place solution using TensorFlow GRU to predict multipliers in forecasting microbusiness density. Adjusted train data using population ratios. Created 56,000 time series for training. Focused on top 90% largest counties and used last known value for small counties. Trained GRU model with GroupKFold and post-processed predictions. Achieved 3rd place Gold. Well done!",
      "votes": 1
    },
    {
      "id": 2311574,
      "postDate": "2023-06-21T08:45:55.210Z",
      "content": "<p>Thanks for sharing. Congratulations Chris!</p>",
      "rawMarkdown": "Thanks for sharing. Congratulations Chris!",
      "votes": 1
    },
    {
      "id": 2311544,
      "postDate": "2023-06-21T08:27:12.997Z",
      "content": "<p>Congratulations! &amp; Thanks a lot for sharing this <a href=\"https://www.kaggle.com/cdeotte\" target=\"_blank\">@cdeotte</a> </p>",
      "rawMarkdown": "Congratulations! & Thanks a lot for sharing this @cdeotte ",
      "votes": 1
    },
    {
      "id": 2311543,
      "postDate": "2023-06-21T08:27:09.993Z",
      "content": "<p>Thanks for sharing Chris, great lesson in how to approach time series forecasting!</p>",
      "rawMarkdown": "Thanks for sharing Chris, great lesson in how to approach time series forecasting!",
      "votes": 1
    },
    {
      "id": 2311365,
      "postDate": "2023-06-21T06:12:49.680Z",
      "content": "<p>Congrats Chris <br>\nAlways coming with very insightful solutions and write-ups </p>",
      "rawMarkdown": "Congrats Chris \nAlways coming with very insightful solutions and write-ups ",
      "votes": 1
    },
    {
      "id": 2310740,
      "postDate": "2023-06-20T15:21:50.717Z",
      "content": "<p>Thanks for sharing, very instructive and concise :)</p>",
      "rawMarkdown": "Thanks for sharing, very instructive and concise :)",
      "votes": 1
    },
    {
      "id": 2310515,
      "postDate": "2023-06-20T12:28:15.673Z",
      "content": "<p>Great explanation, and a very interesting approach - 56K time series wasn't something that came to mind at all!</p>",
      "rawMarkdown": "Great explanation, and a very interesting approach - 56K time series wasn't something that came to mind at all!",
      "votes": 1
    },
    {
      "id": 2310011,
      "postDate": "2023-06-20T03:59:42.077Z",
      "content": "<p>Great job Chris, thank you for sharing. Congrats on 3rd place!</p>",
      "rawMarkdown": "Great job Chris, thank you for sharing. Congrats on 3rd place!",
      "votes": 1
    },
    {
      "id": 2309902,
      "postDate": "2023-06-20T01:08:26.637Z",
      "content": "<p>You know you want to - <a href=\"https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/418308\" target=\"_blank\">https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/418308</a></p>\n<p>:)</p>",
      "rawMarkdown": "You know you want to - https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/418308\n\n:)",
      "votes": 1
    },
    {
      "id": 2309719,
      "postDate": "2023-06-19T20:46:27.380Z",
      "content": "<p>Great job chris.  q:  Did you delete your previous leaderboard post on this?  I couldn't find it and was curious about the diff.</p>",
      "rawMarkdown": "Great job chris.  q:  Did you delete your previous leaderboard post on this?  I couldn't find it and was curious about the diff.",
      "votes": 1,
      "replies": [
        {
          "id": 2309721,
          "postDate": "2023-06-19T20:48:37.717Z",
          "content": "<p>No, my previous post is <a href=\"https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/395098\" target=\"_blank\">here</a></p>",
          "rawMarkdown": "No, my previous post is [here][1]\n\n[1]: https://www.kaggle.com/competitions/godaddy-microbusiness-density-forecasting/discussion/395098",
          "votes": 1
        },
        {
          "id": 2309723,
          "postDate": "2023-06-19T20:50:44.243Z",
          "content": "<p>Congratulations <a href=\"https://www.kaggle.com/kaggleqrdl\" target=\"_blank\">@kaggleqrdl</a> winning first place!</p>",
          "rawMarkdown": "Congratulations @kaggleqrdl winning first place!",
          "votes": 1
        }
      ]
    },
    {
      "id": 2315140,
      "postDate": "2023-06-23T20:54:25.067Z",
      "content": "<p>Congratulations, Chris! Thank you so much for sharing. I have learned some great eye-opening points from this. It helps guide me in looking back at my code again.</p>",
      "rawMarkdown": "Congratulations, Chris! Thank you so much for sharing. I have learned some great eye-opening points from this. It helps guide me in looking back at my code again.",
      "votes": 2
    },
    {
      "id": 2311561,
      "postDate": "2023-06-21T08:37:08.057Z",
      "content": "<p>Ty Chris, your post is always impressive and insightful</p>",
      "rawMarkdown": "Ty Chris, your post is always impressive and insightful",
      "votes": 2
    },
    {
      "id": 2311494,
      "postDate": "2023-06-21T07:32:58.220Z",
      "content": "<p>A big congratulations, I am so happy you win this ❤️ </p>",
      "rawMarkdown": "A big congratulations, I am so happy you win this ❤️ ",
      "votes": 2
    },
    {
      "id": 2309942,
      "postDate": "2023-06-20T02:25:20.063Z",
      "content": "<p>Congratulations <a href=\"https://www.kaggle.com/cdeotte\" target=\"_blank\">@cdeotte</a> and <a href=\"https://www.kaggle.com/kaggleqrdl\" target=\"_blank\">@kaggleqrdl</a> 🎉<br>\nThank for your kind explanation. I have some questions.  </p>\n<ol>\n<li>How is the 1.0045 value obtained through probing used? When predicting 5 values, is it fixed as the first ratio value?</li>\n<li>Will the remaining 10% counties initially have 5 multipliers becoming 1?</li>\n<li>After probing for the remaining 10% counties, will only the first multiplier change to the explored value?</li>\n</ol>",
      "rawMarkdown": "Congratulations @cdeotte and @kaggleqrdl 🎉\nThank for your kind explanation. I have some questions.  \n1. How is the 1.0045 value obtained through probing used? When predicting 5 values, is it fixed as the first ratio value?\n2. Will the remaining 10% counties initially have 5 multipliers becoming 1?\n3. After probing for the remaining 10% counties, will only the first multiplier change to the explored value?",
      "votes": 2,
      "replies": [
        {
          "id": 2310047,
          "postDate": "2023-06-20T04:52:03.593Z",
          "content": "<blockquote>\n  <p>How is the 1.0045 value obtained through probing used? When predicting 5 values, is it fixed as the first ratio value?</p>\n</blockquote>\n<p>After the GRU makes prediction for January, we compute the ratio of \"average January prediction\" divided by \"average December prediction\" for large counties. The result is  <code>1.0032</code>. This is not the optimal ratio. So we multiply every January prediction for large counties by <code>1.0012</code>. Afterward, the the ratio of \"average January prediction\" divided by \"average December prediction\" is <code>1.0045</code> and our public LB and private LB are boosted.</p>\n<p>Regarding the small counties, each begins with multiplier of <code>1</code> which means that each small county prediction uses the December 2022 value. We then try different multipliers for different small counties and keep ones that improve LB. Basically we are finding what the small counties ground truth is for January 2023. Then our final submission uses the January values for small counties instead of December values for small counties. This boosts public and private LB.</p>\n<p>Both post processes combined improve CV and LB by about <code>+0.05</code></p>",
          "rawMarkdown": ">How is the 1.0045 value obtained through probing used? When predicting 5 values, is it fixed as the first ratio value?\n\nAfter the GRU makes prediction for January, we compute the ratio of \"average January prediction\" divided by \"average December prediction\" for large counties. The result is  `1.0032`. This is not the optimal ratio. So we multiply every January prediction for large counties by `1.0012`. Afterward, the the ratio of \"average January prediction\" divided by \"average December prediction\" is `1.0045` and our public LB and private LB are boosted.\n\nRegarding the small counties, each begins with multiplier of `1` which means that each small county prediction uses the December 2022 value. We then try different multipliers for different small counties and keep ones that improve LB. Basically we are finding what the small counties ground truth is for January 2023. Then our final submission uses the January values for small counties instead of December values for small counties. This boosts public and private LB.\n\nBoth post processes combined improve CV and LB by about `+0.05`",
          "votes": 3,
          "replies": [
            {
              "id": 2318233,
              "postDate": "2023-06-26T08:50:26.033Z",
              "content": "<p>Congrats! May I ask what is \"average December prediction\"? Is it predict by the 1st multiplier multiply Nov's MD?</p>",
              "rawMarkdown": "Congrats! May I ask what is \"average December prediction\"? Is it predict by the 1st multiplier multiply Nov's MD?"
            }
          ]
        }
      ]
    },
    {
      "id": 2375531,
      "postDate": "2023-08-05T17:43:19.343Z",
      "content": "<p>Congratulations Chris. Thank you so much for sharing. </p>",
      "rawMarkdown": "Congratulations Chris. Thank you so much for sharing. "
    },
    {
      "id": 2321040,
      "postDate": "2023-06-28T08:37:07.310Z",
      "content": "<p>hi Chris！Most people (including me) predict the rate of change (i.e. multiplier) or growth rate, while few people directly predict the density of enterprises. However, I am only because the former performs better in various verifications and results. Can there be some explanation from a theoretical perspective? Looking forward to your reply!</p>",
      "rawMarkdown": "hi Chris！Most people (including me) predict the rate of change (i.e. multiplier) or growth rate, while few people directly predict the density of enterprises. However, I am only because the former performs better in various verifications and results. Can there be some explanation from a theoretical perspective? Looking forward to your reply!"
    },
    {
      "id": 2318429,
      "postDate": "2023-06-26T11:10:49.527Z",
      "content": "<p><strong>multiplier</strong>,Simple but wonderful!!!</p>",
      "rawMarkdown": "**multiplier**,Simple but wonderful!!!"
    },
    {
      "id": 2317205,
      "postDate": "2023-06-25T14:03:07.080Z",
      "content": "<p>Congrats and thanks for sharing.</p>",
      "rawMarkdown": "Congrats and thanks for sharing.",
      "votes": 1
    },
    {
      "id": 2310831,
      "postDate": "2023-06-20T16:24:10.607Z",
      "content": "<p>Thanks for posting!</p>",
      "rawMarkdown": "Thanks for posting!",
      "votes": 2
    },
    {
      "id": 2310691,
      "postDate": "2023-06-20T14:49:21.990Z",
      "content": "<p>thanks for sharing!</p>",
      "rawMarkdown": "thanks for sharing!",
      "votes": 2
    },
    {
      "id": 2315690,
      "postDate": "2023-06-24T10:20:31.407Z",
      "content": "<p>Thanks for sharing. Congrats!</p>",
      "rawMarkdown": "Thanks for sharing. Congrats!",
      "votes": 2,
      "isDeleted": true
    }
  ],
  "complete": true,
  "source": "live",
  "fetched_at": "2026-10-19T19:29:22Z",
  "competition_id": 41881,
  "competition_slug": "godaddy-microbusiness-density-forecasting",
  "team_id": 9631671,
  "solution_url": "/competitions/godaddy-microbusiness-density-forecasting/writeups/chris-deotte-3rd-place-predict-multipliers-with-gr"
}