/// <summary>
        /// Replaces the provider of the expression with the given one.
        /// </summary>
        /// <typeparam name="TEntity">The type of the entity.</typeparam>
        /// <param name="query">The query.</param>
        /// <param name="set">The set.</param>
        /// <param name="provider">The provider of the set.</param>
        /// <returns></returns>
        /// <exception cref="ArgumentNullException">
        /// query
        /// or
        /// set
        /// or
        /// provider
        /// </exception>
        /// <exception cref="ArgumentException">The supplied query does not originate from a QueryRootExpression and therefor does not come from Entity Framework. - query</exception>
        public static Expression ReplaceProvider <TEntity>(Expression query, DbSet <TEntity> set, IQueryProvider provider)
            where TEntity : class
        {
            if (query is null)
            {
                throw new ArgumentNullException(nameof(query));
            }
            if (set is null)
            {
                throw new ArgumentNullException(nameof(set));
            }
            if (provider is null)
            {
                throw new ArgumentNullException(nameof(provider));
            }

            var setQuery = provider is IAsyncQueryProvider asyncProvider ?
                           new QueryRootExpression(asyncProvider, set.EntityType) :
                           new QueryRootExpression(set.EntityType);

            var visitor  = new QueryRootExpressionReplaceVisitor(setQuery);
            var replaced = visitor.Visit(query);

            if (!visitor.queryWasReplaced)
            {
                throw new ArgumentException($"The supplied query does not originate from a {nameof(QueryRootExpression)} and therefor does not come from Entity Framework.", nameof(query));
            }

            return(replaced ?? throw new ArgumentException($"The supplied query resulted in a replaces expression which was null. This should not happen.", nameof(query)));
        }
 private static Expression ReplaceProvider(Expression query, DbSet <TEntity> set, IQueryProvider provider)
 => QueryRootExpressionReplaceVisitor.ReplaceProvider(query, set, provider);