aboutsummaryrefslogtreecommitdiffstats
path: root/contrib/clickhouse/src/Planner/PlannerActionsVisitor.h
blob: 8506c3091718d48041454b7c12b4a98a93fac97a (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
#pragma once

#include <Core/Names.h>
#include <Core/NamesAndTypes.h>

#include <Interpreters/Context_fwd.h>

#include <Analyzer/IQueryTreeNode.h>

#include <Interpreters/ActionsDAG.h>

namespace DB
{

class PlannerContext;
using PlannerContextPtr = std::shared_ptr<PlannerContext>;

/** Planner actions visitor is responsible for adding necessary actions to calculate query tree expression node
  * into actions dag.
  *
  * Preconditions:
  * 1. Table expression data for table expression nodes is collected in planner context.
  * For column node, that has column table expression source, identifier for column name in table expression data
  * is used as action dag node name, if use_column_identifier_as_action_node_name = true.
  * 2. Sets for IN functions are already collected in planner context.
  *
  * During actions build, there is special handling for following functions:
  * 1. Aggregate functions are added in actions dag as INPUT nodes. Aggregate functions arguments are not added.
  * 2. For function `in` and its variants, already collected sets from planner context are used.
  */
class PlannerActionsVisitor
{
public:
    explicit PlannerActionsVisitor(const PlannerContextPtr & planner_context_, bool use_column_identifier_as_action_node_name_ = true);

    /** Add actions necessary to calculate expression node into expression dag.
      * Necessary actions are not added in actions dag output.
      * Returns query tree expression node actions dag nodes.
      */
    ActionsDAG::NodeRawConstPtrs visit(ActionsDAGPtr actions_dag, QueryTreeNodePtr expression_node);

private:
    const PlannerContextPtr planner_context;
    bool use_column_identifier_as_action_node_name = true;
};

/** Calculate query tree expression node action dag name and add them into node to name map.
  * If node exists in map, name from map is used.
  *
  * For column node column node identifier from planner context is used, if use_column_identifier_as_action_node_name = true.
  */
using QueryTreeNodeToName = std::unordered_map<QueryTreeNodePtr, String>;
String calculateActionNodeName(const QueryTreeNodePtr & node,
    const PlannerContext & planner_context,
    QueryTreeNodeToName & node_to_name,
    bool use_column_identifier_as_action_node_name = true);

/** Calculate query tree expression node action dag name.
  *
  * For column node column node identifier from planner context is used, if use_column_identifier_as_action_node_name = true.
  */
String calculateActionNodeName(const QueryTreeNodePtr & node,
    const PlannerContext & planner_context,
    bool use_column_identifier_as_action_node_name = true);

/// Calculate action node name for constant
String calculateConstantActionNodeName(const Field & constant_literal, const DataTypePtr & constant_type);

/// Calculate action node name for constant, data type will be derived from constant literal value
String calculateConstantActionNodeName(const Field & constant_literal);

/** Calculate action node name for window node.
  * Window node action name can only be part of window function action name.
  * For column node column node identifier from planner context is used, if use_column_identifier_as_action_node_name = true.
  */
String calculateWindowNodeActionName(const QueryTreeNodePtr & node,
    const PlannerContext & planner_context,
    QueryTreeNodeToName & node_to_name,
    bool use_column_identifier_as_action_node_name = true);

/** Calculate action node name for window node.
  * Window node action name can only be part of window function action name.
  * For column node column node identifier from planner context is used, if use_column_identifier_as_action_node_name = true.
  */
String calculateWindowNodeActionName(const QueryTreeNodePtr & node,
    const PlannerContext & planner_context,
    bool use_column_identifier_as_action_node_name = true);

}