void pruneExpressions() {
   for (Set<ExpressionContext> ecSet : allExprsQueried.values()) {
     for (ExpressionContext ec : ecSet) {
       Set<ExprSpecContext> removedEsc = new HashSet<ExprSpecContext>();
       for (Iterator<ExprSpecContext> iterator = ec.getAllExprs().iterator();
           iterator.hasNext(); ) {
         ExprSpecContext esc = iterator.next();
         boolean removed = false;
         // Go over expression dims and remove expression involving dimensions for which
         // candidate tables are
         // not there
         for (Dimension exprDim : esc.exprDims) {
           if (cubeql.getCandidateDims().get(exprDim) == null
               || cubeql.getCandidateDims().get(exprDim).isEmpty()) {
             log.info(
                 "Removing expression {} as {} it does not have any candidate tables",
                 esc,
                 exprDim);
             iterator.remove();
             removedEsc.add(esc);
             removed = true;
             break;
           }
         }
         if (removed) {
           continue;
         }
         // remove expressions which are not valid in the timerange queried
         // If an expression is defined as
         // ex = a + b // from t1 to t2;
         // ex = c + d // from t2 to t3
         // With range queried, invalid expressions will be removed
         // If range is including more than one expression, queries can be unioned as an
         // improvement at later time.
         // But for now, they are not eligible expressions
         for (TimeRange range : cubeql.getTimeRanges()) {
           if (!esc.isValidInTimeRange(range)) {
             log.info("Removing expression {} as it is not valid in timerange queried", esc);
             iterator.remove();
             removedEsc.add(esc);
             removed = true;
             break;
           }
         }
         if (removed) {
           continue;
         }
         // Go over expressions and remove expression containing unavailable columns in timerange
         // In the example above,
         // if ex = a +b ; and a is not available in timerange queried, it will be removed.
         for (TimeRange range : cubeql.getTimeRanges()) {
           boolean toRemove = false;
           for (Map.Entry<String, Set<String>> entry : esc.getTblAliasToColumns().entrySet()) {
             if (CubeQueryContext.DEFAULT_TABLE.equalsIgnoreCase(entry.getKey())) {
               continue;
             }
             AbstractBaseTable baseTable =
                 (AbstractBaseTable) cubeql.getCubeTableForAlias(entry.getKey());
             for (String col : entry.getValue()) {
               if (!baseTable.getColumnByName(col).isColumnAvailableInTimeRange(range)) {
                 toRemove = true;
                 break;
               }
             }
             if (toRemove) {
               break;
             }
           }
           if (toRemove) {
             log.info(
                 "Removing expression {} as its columns are unavailable in timerange queried",
                 esc);
             iterator.remove();
             removedEsc.add(esc);
             removed = true;
             break;
           }
         }
       }
       for (Set<ExprSpecContext> evalSet : ec.evaluableExpressions.values()) {
         evalSet.removeAll(removedEsc);
       }
     }
   }
 }