public T ExecuteQuery <T>(
            IExecutionPlan <T> plan,
            IExecutionContext context)
        {
            ITable[] tables = TableLocator.FindAffectedTables(context.Database, plan);

            for (int i = 0; i < tables.Length; i++)
            {
                this.AcquireReadLock(tables[i], context);
            }

            try
            {
                var item = plan.Execute(context);

                EntityPropertyCloner <T> cloner = null;
                if (this.database.Tables.IsEntityType <T>())
                {
                    cloner = EntityPropertyCloner <T> .Instance;
                }
                if (cloner != null && item != null)
                {
                    var cloned = Activator.CreateInstance <T>();
                    cloner.Clone(item, cloned);

                    // Remove Aliased Attributes these are getting added by the Query Plan Execution
#pragma warning disable IDE0019 // Use pattern matching
                    var entity = item as Entity;
#pragma warning restore IDE0019 // Use pattern matching
                    if (entity != null)
                    {
                        foreach (var attribute in entity.Attributes.ToList().Where(attribute => attribute.Value is AliasedValue))
                        {
                            entity.Attributes.Remove(attribute.Key);
                        }
                    }

                    return(cloned);
                }
                else
                {
                    return(item);
                }
            }
            finally
            {
                for (int i = 0; i < tables.Length; i++)
                {
                    this.ReleaseReadLock(tables[i], context);
                }
            }
        }
        private IEnumerator <T> ExecuteQuery <T>(
            IExecutionPlan <IEnumerable <T> > plan,
            IExecutionContext context,
            ITable[] tablesToLock,
            bool cloneEntities)
        {
            ITable[] tables = TableLocator.FindAffectedTables(context.Database, plan);

            EntityPropertyCloner <T> cloner = null;

            if (cloneEntities && this.database.Tables.IsEntityType <T>())
            {
                cloner = EntityPropertyCloner <T> .Instance;
            }

            LinkedList <T> result = new LinkedList <T>();

            for (int i = 0; i < tablesToLock.Length; i++)
            {
                this.AcquireReadLock(tablesToLock[i], context);
            }

            IEnumerable <T> query = plan.Execute(context);

            try
            {
                foreach (T item in query)
                {
                    if (cloner != null)
                    {
                        T resultEntity = Activator.CreateInstance <T>();
                        cloner.Clone(item, resultEntity);

                        result.AddLast(resultEntity);

                        // Remove Aliased Attributes these are getting added by the Query Plan Execution
#pragma warning disable IDE0019 // Use pattern matching
                        var entity = item as Entity;
#pragma warning restore IDE0019 // Use pattern matching
                        if (entity != null)
                        {
                            foreach (var attribute in entity.Attributes.ToList().Where(attribute => attribute.Value is AliasedValue))
                            {
                                entity.Attributes.Remove(attribute.Key);
                            }
                        }
                    }
                    else
                    {
                        result.AddLast(item);
                    }
                }
            }
            finally
            {
                for (int i = 0; i < tablesToLock.Length; i++)
                {
                    this.ReleaseReadLock(tablesToLock[i], context);
                }
            }

            return(result.GetEnumerator());
        }