2
\$\begingroup\$

I have this query built using the above, but it feels like it could be improved to make it more concise:

  private IQueryable<Lead> _queryLeadsByHeat(int? ownerUserId, bool warmLeads)
        {
            var predicate = PredicateBuilder.False<Lead>();

            predicate = predicate.Or(x => x.LeadPool.DecreaseByUnit == (int) DecreaseUnitTime.Day
                                           &&
                                           (
                                               (x.LastHeatValue - SqlFunctions.DateDiff("day", !x.LastContactDate.HasValue
                                                                          ? x.InitialContactDate
                                                                          : x.LastContactDate.Value, DateTime.Today) * x.LeadPool.DecreaseLeadBy) > 0 && warmLeads ||

                                                (x.LastHeatValue - SqlFunctions.DateDiff("day", !x.LastContactDate.HasValue
                                                                          ? x.InitialContactDate
                                                                          : x.LastContactDate.Value, DateTime.Today)*
                                                x.LeadPool.DecreaseLeadBy) <= 0 && !warmLeads
                                            )
                                       );

            predicate = predicate.Or(x => x.LeadPool.DecreaseByUnit == (int)DecreaseUnitTime.Week
                                       &&
                                       (
                                           (x.LastHeatValue - SqlFunctions.DateDiff("week", !x.LastContactDate.HasValue
                                                                      ? x.InitialContactDate
                                                                      : x.LastContactDate.Value, DateTime.Today) * x.LeadPool.DecreaseLeadBy) > 0 && warmLeads ||

                                            (x.LastHeatValue - SqlFunctions.DateDiff("week", !x.LastContactDate.HasValue
                                                                      ? x.InitialContactDate
                                                                      : x.LastContactDate.Value, DateTime.Today) *
                                            x.LeadPool.DecreaseLeadBy) <= 0 && !warmLeads
                                        )
                                   );


            predicate = predicate.Or(x => x.LeadPool.DecreaseByUnit == (int)DecreaseUnitTime.Month
                                       &&
                                       (
                                           (x.LastHeatValue - SqlFunctions.DateDiff("month", !x.LastContactDate.HasValue
                                                                      ? x.InitialContactDate
                                                                      : x.LastContactDate.Value, DateTime.Today) * x.LeadPool.DecreaseLeadBy) > 0 && warmLeads ||

                                            (x.LastHeatValue - SqlFunctions.DateDiff("month", !x.LastContactDate.HasValue
                                                                      ? x.InitialContactDate
                                                                      : x.LastContactDate.Value, DateTime.Today) *
                                            x.LeadPool.DecreaseLeadBy) <= 0 && !warmLeads
                                        )
                                   );


            var query = _activeLeads(ownerUserId)            
                        .AsExpandable().Where(predicate);

            return query;
        }

Any ideas on how to improve this?

\$\endgroup\$
1
\$\begingroup\$

First of all. Is _queryLeadsByHeat supposed to represent a method? If so I would steer away from using underscore in it's method name unless that's your naming convention in which case I guess your stuck with it. Underscore is traditionally mainly reserved for fields (if at all as there are large debates for this practice).

I don't have Visual studio in front of me so not sure if this will even compile (or is even possible) but my initial thought would be to try and consolidate the Predicates into one method.

Expression<Func<T, bool>> GetHeatCondition(DecreaseUnitTime period)
{
    string periodAsString = period.ToString();

    return predicate.Or(x => x.LeadPool.DecreaseByUnit == (int)period
                               &&
                               (
                                   (x.LastHeatValue - SqlFunctions.DateDiff(periodAsString, !x.LastContactDate.HasValue
                                                              ? x.InitialContactDate
                                                              : x.LastContactDate.Value, DateTime.Today) * x.LeadPool.DecreaseLeadBy) > 0 && warmLeads ||

                                    (x.LastHeatValue - SqlFunctions.DateDiff(periodAsString, !x.LastContactDate.HasValue
                                                              ? x.InitialContactDate
                                                              : x.LastContactDate.Value, DateTime.Today) *
                                    x.LeadPool.DecreaseLeadBy) <= 0 && !warmLeads
                                )
                           );
}

private IQueryable<Lead> QueryLeadsByHeat(int? ownerUserId, bool warmLeads)
{
    var predicate = PredicateBuilder.False<Lead>();
    predicate = predicate.Or(GetHeatCondition<Lead>(DecreaseUnitTime.Day));
    predicate = predicate.Or(GetHeatCondition<Lead>(DecreaseUnitTime.Month));
    predicate = predicate.Or(GetHeatCondition<Lead>(DecreaseUnitTime.Year));

    var query = _activeLeads(ownerUserId)            
                        .AsExpandable().Where(predicate);

            return query;
}

I'm pretty sure that Linq query could be better optimized. Have to think some more on that one...

| improve this answer | |
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.