private void AllocateRetiredEarlyBeforeSocialAndPension(int r401KAge, int pensionAge, int maxAge)
        {
            for (var year = r401KAge; year < pensionAge; year++)
            {
                var preDto    = AllocationDict[year - 1];
                var preAssets = preDto.Assets;

                var assetDate   = new DateTime(year, 12, 31);
                var transformer = new SimpleTransformer(_settings.InvestmentReturnRate);
                var assets      = transformer.Transform(assetDate, preAssets);

                // 401K
                var r401Amount = SimpleR401KAllocator.Allocate(assets, maxAge, year);

                // Cash
                var target         = GetTarget(preDto);
                var cashAmount     = r401Amount >= target ? 0m : target - r401Amount;
                var cashWithdrawal = SimpleAllocator.Allocate(assets, assets.ForCash(), cashAmount);

                var preTotal = preDto.AssetTotal;
                var curTotal = assets.Sum(x => x.AssetAmount);

                var dto = new AllocationDto(year, AllocationStatusTypes.RetiredEstimated, target)
                {
                    AgeYear           = new RetirementAge(year - BirthYear, year).ToString(),
                    CashAmount        = cashWithdrawal,
                    R401KAmount       = r401Amount,
                    Assets            = assets.ToArray(),
                    PreAssets         = preDto.Assets,
                    AssetTotalChanged = AssetsHelper.GetTotalWithChange(curTotal, preTotal)
                };
                AllocationDict.Add(year, dto);
            }
        }
        private void AllocateRetiredFully(int pensionAge, int maxAge)
        {
            for (var year = pensionAge; year < maxAge; year++)
            {
                var preDto    = AllocationDict[year - 1];
                var preAssets = preDto.Assets;

                var assetDate   = new DateTime(year, 12, 31);
                var transformer = new SimpleTransformer(_settings.InvestmentReturnRate);
                var assets      = transformer.Transform(assetDate, preAssets);

                // 401K
                var r401Amount = SimpleR401KAllocator.Allocate(assets, maxAge, year);

                // Cash
                var target         = GetTarget(preDto);
                var cashPortion    = (target - r401Amount - PensionIncome - SocialSecurityIncome);
                var cashAmount     = cashPortion >= 0 ? cashPortion : 0m;
                var cashWithdrawal = SimpleAllocator.Allocate(assets, assets.ForCash(), cashAmount);

                // Still missing target
                var shortAmount = target - cashWithdrawal - r401Amount - SocialSecurityIncome - PensionIncome;
                if (shortAmount > 0)
                {
                    r401Amount += SimpleAllocator.Allocate(assets, assets.For401K(), shortAmount);
                }

                var preTotal = preDto.AssetTotal;
                var curTotal = assets.Sum(x => x.AssetAmount);

                var dto = new AllocationDto(year, AllocationStatusTypes.RetiredEstimated, target)
                {
                    AgeYear              = new RetirementAge(year - BirthYear, year).ToString(),
                    CashAmount           = cashWithdrawal,
                    R401KAmount          = r401Amount,
                    SocialSecurityAmount = SocialSecurityIncome,
                    PensionAmount        = PensionIncome,
                    Assets            = assets.ToArray(),
                    PreAssets         = preDto.Assets,
                    AssetTotalChanged = AssetsHelper.GetTotalWithChange(curTotal, preTotal)
                };
                AllocationDict.Add(year, dto);
            }
        }