Using Dictionary of int and list of tuple in C# I have implemented mathematical functions using a C# library. I basically need to output data by the RiskMatrixByFunds in the following format.

Key will contain Id and value will contain collection of string, double, double  

For example:

Id 1

value 

{'ArithmeticMean', 12.34, 3.44},
{'AverageGain', 12.35, 3.45},
{'AverageLoss', 12.36, 3.46},


I have used a Dictionary structure that will contain the int and list of tuple collection.

Let me know if it can be enhanced, any ideas on magic strings used, a better way to implement it.

public class RiskMatrix : IRiskMatrix
{

    public (double Monthly, double Annual) ArithmeticMean(IEnumerable&lt;double&gt; ReturnsList)
    {
        double returnList = ReturnsList.Mean();
        return (Monthly: returnList, Annual: returnList * Math.Pow(12, 0.5));
    }

    public (double Monthly, double Annual) AverageGain(IEnumerable&lt;double&gt; ReturnsList)
    {

        double returnList = ReturnsList.GainMean();
        return (Monthly: returnList, Annual: returnList * Math.Pow(12, 0.5));
    }

    public (double Monthly, double Annual) AverageLoss(IEnumerable&lt;double&gt; ReturnsList)
    {
        double returnList = ReturnsList.LossMean();
        return (Monthly: returnList, Annual: returnList * Math.Pow(12, 0.5));
    }


    public Dictionary&lt;int, List&lt;Tuple&lt;string,double, double&gt;&gt;&gt; RiskMatrixByFunds(Dictionary&lt;int, IEnumerable&lt;double&gt;&gt; ReturnsList)
    {
        Dictionary&lt;int, List&lt;Tuple&lt;string ,double, double&gt;&gt;&gt; returnsList = new Dictionary&lt;int, List&lt;Tuple&lt;string,double, double&gt;&gt;&gt;();
        List &lt;Tuple&lt;string, double, double&gt;&gt; list = null;

        foreach (KeyValuePair&lt;int, IEnumerable&lt;double&gt;&gt; entry in ReturnsList)
        {
            list = new List&lt;Tuple&lt;string, double, double&gt;&gt;();
            (double Monthly, double Annual) arithmeticMeanResult = ArithmeticMean(entry.Value);
            list.Add(new Tuple&lt;string, double, double&gt;("ArithmeticMean", arithmeticMeanResult.Monthly, arithmeticMeanResult.Annual));
            (double Monthly, double Annual) averageGainResult = AverageGain(entry.Value);
            list.Add(new Tuple&lt;string, double, double&gt;("AverageGain", averageGainResult.Monthly, averageGainResult.Annual));
            (double Monthly, double Annual) averageLossResult = AverageLoss(entry.Value);
            list.Add(new Tuple&lt;string, double, double&gt;("AverageLoss", averageLossResult.Monthly, averageLossResult.Annual));
            (double Monthly, double Annual) betaCorrelationresult = BetaCorrelation(entry.Value);

           returnsList.Add(entry.Key, list);
        }
        return returnsList;
    }   
}
There might be a reason why you used a List&lt;Tuple&lt;string ,double, double&gt;&gt;. E.g. if you need to pass the data to an existing library or your UI needs to bind to a list. Otherwise I would recommend to create a dedicated class

public class RiskStatistics
{
    public double ArithmeticMeanMonthly { get; set; }
    public double ArithmeticMeanAnnual { get; set; }

    public double AverageGainMonthly { get; set; }
    public double AverageGainAnnual { get; set; }

    public double AverageLossMonthly { get; set; }
    public double AverageLossAnnual { get; set; }
}


Since the properties are named, there's no need for magic strings. This makes the creation and usage of the risk matrix less convoluted:

public Dictionary&lt;int, RiskStatistics&gt; RiskMatrixByFunds(
    Dictionary&lt;int, IEnumerable&lt;double&gt;&gt; returnsLists)
{
    var riskMatrixDict = new Dictionary&lt;int, RiskStatistics&gt;();

    foreach (KeyValuePair&lt;int, IEnumerable&lt;double&gt;&gt; entry in returnsLists) {
        var risk = new RiskStatistics();
        (risk.ArithmeticMeanMonthly, risk.ArithmeticMeanAnnual) = ArithmeticMean(entry.Value);
        (risk.AverageGainMonthly, risk.AverageGainAnnual) = AverageGain(entry.Value);
        (risk.AverageLossMonthly, risk.AverageLossAnnual) = AverageLoss(entry.Value);
        riskMatrixDict.Add(entry.Key, risk);
    }
    return riskMatrixDict;
}




You could also calculate the annual values on the fly. This would make the creation even easier. Here the adapted average gain properties as an example:

private static readonly double Sqrt12 = Math.Pow(12, 0.5);

public double ArithmeticMeanMonthly { get; set; }
public double ArithmeticMeanAnnual =&gt; ArithmeticMeanMonthly * Sqrt12;


With this adapted RiskStatistics class, you could directly assign from the extension methods and skip the methods returning tuples.

var risk = new RiskStatistics {
    ArithmeticMeanMonthly = entry.Value.Mean(),
    AverageGainMonthly = entry.Value.GainMean(),
    AverageLossMonthly = entry.Value.LossMean()
};
riskMatrixDict.Add(entry.Key, risk);


The annual values are read-only and need not to be assigned.