/// <summary>Visits a where clause.</summary>
        /// <param name="whereClause">Where clause to be visited.</param>
        /// <param name="queryModel">Query model containing given from clause.</param>
        /// <param name="index">Index of the where clause in the query model.</param>
        public override void VisitWhereClause(WhereClause whereClause, Remotion.Linq.QueryModel queryModel, int index)
        {
            _visitor.ConstantFromClause = _auxFromComponent;
            _visitor.Visit(whereClause.Predicate);
            QueryComponent           queryComponent          = _visitor.RetrieveComponent();
            IQueryComponentNavigator queryComponentNavigator = queryComponent.GetQueryComponentNavigator();

            if (queryComponentNavigator != null)
            {
                queryComponentNavigator.ReplaceComponent(Identifier.Current, _subject);
            }

            if (queryComponent is QueryElement)
            {
                if ((!(queryComponent is EntityConstrain)) && (!_query.Elements.Contains((QueryElement)queryComponent)))
                {
                    _query.Elements.Add((QueryElement)queryComponent);
                }
            }
            else if (!_query.FindAllComponents <Filter>().Any(item => item.Expression == queryComponent))
            {
                Filter filter = new Filter((IExpression)queryComponent);
                StrongEntityAccessor targetEntityAccessor = null;
                if ((_subject != _mainFromComponent.About) && (queryComponentNavigator.Contains(_subject)))
                {
                    targetEntityAccessor = (from entityAccessor in _query.FindAllComponents <StrongEntityAccessor>()
                                            from constrain in entityAccessor.FindAllComponents <EntityConstrain>()
                                            where (constrain.GetType() == typeof(EntityConstrain)) && (_subject.Equals(constrain.Value))
                                            select entityAccessor).FirstOrDefault();
                }

                if (targetEntityAccessor == null)
                {
                    IEnumerable <StrongEntityAccessor> targetEntityAccessorExression = _query.Elements.OfType <StrongEntityAccessor>();
                    if ((_query.IsSubQuery) || (whereClause.Predicate is Remotion.Linq.Clauses.Expressions.SubQueryExpression))
                    {
                        targetEntityAccessorExression = targetEntityAccessorExression.Except(new StrongEntityAccessor[] { _query.Elements.OfType <StrongEntityAccessor>().LastOrDefault() });
                    }

                    targetEntityAccessor = targetEntityAccessorExression.LastOrDefault() ?? _mainFromComponent;
                }

                if ((!targetEntityAccessor.Elements.Contains(queryComponent)) && (!targetEntityAccessor.Elements.Contains(filter)))
                {
                    targetEntityAccessor.Elements.Add(filter);
                }
            }

            _auxFromComponent = null;
            base.VisitWhereClause(whereClause, queryModel, index);
        }
        internal static bool Contains(this IQueryComponentNavigator navigator, IQueryComponent component)
        {
            bool result = navigator.ContainsComponent(component);

            if (!result)
            {
                foreach (IQueryComponent childComponent in navigator.GetComponents())
                {
                    IQueryComponentNavigator childNavigator = childComponent.GetQueryComponentNavigator();
                    if (childNavigator != null)
                    {
                        bool localResult = childNavigator.Contains(component);
                        if (localResult)
                        {
                            result = localResult;
                            break;
                        }
                    }
                }
            }

            return(result);
        }