/// <summary>
        /// Randomly select a triad type, then a card to keep the distribution even between types.
        /// </summary>        
        public override Flashcard Next()
        {
            var typeArray = Enum.GetValues(typeof(TriadType)).Cast<TriadType>().Where(t => t != TriadType.All).ToArray();
            var selectedTypes = typeArray.Where(t => TriadTypes.HasFlag(t)).ToArray();

            if (selectedTypes.Count() > 1)
            {
                // if there's more than one selected type, we want an even distribution of triad types, not
                // weighted toward the types that have more cards.  create an array of single-type generators
                // and randomly select one each time Next is called.
                if (_generators == null)
                {
                    _generators = new TriadFlashcardGenerator[selectedTypes.Count()];
                    for (int i = 0; i < _generators.Length; i++)
                    {
                        var args = new TradFlashcardGeneratorArgs();
                        args.TriadTypes = selectedTypes[i];
                        args.TriadInversions = TriadInversions;
                        args.Accidentals = Accidentals;
                        args.Staffs = Staffs;
                        _generators[i] = new TriadFlashcardGenerator(args);
                    }
                }
                var randomType = r.Next(selectedTypes.Length);
                return _generators[randomType].Next();
            }

            // only one selected type - call base which will randomly select a flashcard.
            return base.Next();
        }
        /// <summary>
        /// Creates a new TriadFlashcardGenerator.
        /// </summary>
        /// <param name="triadTypes">This flags value indicates which types of triads to include.</param>
        /// <param name="triadInversions">This flags value indicates which triad inversions to include.</param>
        /// <param name="staffs">This flags value indicates which staffs to include.</param>
        public TriadFlashcardGenerator(TradFlashcardGeneratorArgs args)
            : base(args)
        {
            if(args.TriadInversions == 0)
                throw new ArgumentException("Need at least one triad inversion to construct a triad flashcard generator.");
            if (args.TriadTypes == 0)
                throw new ArgumentException("Need at least one triad type to construct a triad flashcard generator.");

            TriadInversions = args.TriadInversions;
            TriadTypes = args.TriadTypes;

            if (Accidentals == AccidentalType.Natural)
            {
                // there just aren't enough diminished and augmented triads representable without accidentals, so skip them.
                TriadTypes &= ~TriadType.Augmented;
                TriadTypes &= ~TriadType.Diminished;
            }
        }