public static EncryptorWithChecksum <TEncryptor, THasher> CreateEncryptor <TEncryptor, THasher>(
            [NotNull] string secretKey,
            out string randomSalt,
            ByteArrayStringEncoding saltEncoding = ConvertByteArray.DefaultStringEncoding,
            EncryptionOptions options            = DefaultOptions)
            where TEncryptor : SymmetricAlgorithm
            where THasher : KeyedHashAlgorithm
        {
            Contract.Requires <ArgumentNullException>(secretKey != null);

            byte[] randomSaltBytes;
            EncryptorWithChecksum <TEncryptor, THasher> encryptor = CreateEncryptor <TEncryptor, THasher>(
                secretKey, out randomSaltBytes, options);

            randomSalt = randomSaltBytes.ToEncodedString(saltEncoding);

            return(encryptor);
        }
        public static EncryptorWithChecksum CreateEncryptor(
            [NotNull] this SymmetricAlgorithm algorithm,
            [NotNull] KeyedHashAlgorithm checksumHasher,
            [NotNull] string password,
            out string randomSalt,
            ByteArrayStringEncoding saltEncoding = ConvertByteArray.DefaultStringEncoding,
            EncryptionOptions options            = DefaultOptions)
        {
            Contract.Requires <ArgumentNullException>(algorithm != null);
            Contract.Requires <ArgumentNullException>(checksumHasher != null);
            Contract.Requires <ArgumentNullException>(password != null);

            byte[] randomSaltBytes;
            EncryptorWithChecksum encryptor = algorithm.CreateEncryptor(
                checksumHasher, password, out randomSaltBytes, options);

            randomSalt = randomSaltBytes.ToEncodedString(saltEncoding);

            return(encryptor);
        }