tuple.h 5.3 KB
Newer Older
羽飞's avatar
羽飞 已提交
1 2 3 4 5 6 7 8 9 10 11
/* Copyright (c) 2021 Xie Meiyi(xiemeiyi@hust.edu.cn) and OceanBase and/or its affiliates. All rights reserved.
miniob is licensed under Mulan PSL v2.
You can use this software according to the terms and conditions of the Mulan PSL v2.
You may obtain a copy of Mulan PSL v2 at:
         http://license.coscl.org.cn/MulanPSL2
THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
See the Mulan PSL v2 for more details. */

//
12
// Created by Meiyi & Wangyunlai on 2021/5/14.
羽飞's avatar
羽飞 已提交
13 14
//

羽飞's avatar
羽飞 已提交
15
#pragma once
羽飞's avatar
羽飞 已提交
16 17 18 19

#include <memory>
#include <vector>

羽飞's avatar
羽飞 已提交
20
#include "common/log/log.h"
羽飞's avatar
羽飞 已提交
21 22
#include "sql/parser/parse.h"
#include "sql/executor/value.h"
羽飞's avatar
羽飞 已提交
23 24
#include "storage/common/field.h"
#include "storage/common/record.h"
羽飞's avatar
羽飞 已提交
25 26 27

class Table;

羽飞's avatar
羽飞 已提交
28 29
class TupleCellSpec
{
羽飞's avatar
羽飞 已提交
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
public:
  TupleCellSpec() = default;
  TupleCellSpec(const char *table_name, const char *field_name, const char *alias)
    : table_name_(table_name), field_name_(field_name), alias_(alias)
  {}

  void set_table_name(const char *table_name)
  {
    this->table_name_ = table_name;
  }

  void set_field_name(const char *field_name)
  {
    this->field_name_ = field_name;
  }

  void set_alias(const char *alias)
  {
    this->alias_ = alias;
  }
  const char *table_name() const
  {
    return table_name_;
  }
  const char *field_name() const
  {
    return field_name_;
  }
  const char *alias() const
  {
    return alias_;
  }

  bool is_same_cell(const TupleCellSpec &other) const
  {
    return 0 == strcmp(this->table_name_, other.table_name_) &&
      0 == strcmp(this->field_name_, other.field_name_);
  }

private:
  // TODO table and field cannot describe all scenerio, should be expression
  const char *table_name_ = nullptr;
  const char *field_name_ = nullptr;
  const char *alias_ = nullptr;
羽飞's avatar
羽飞 已提交
74 75 76 77
};

class Tuple
{
羽飞's avatar
羽飞 已提交
78 79
public:
  Tuple() = default;
羽飞's avatar
羽飞 已提交
80
  virtual ~Tuple() = default;
羽飞's avatar
羽飞 已提交
81

羽飞's avatar
羽飞 已提交
82 83
  virtual int cell_num() const = 0; 
  virtual RC  cell_at(int index, TupleCell &cell) const = 0;
羽飞's avatar
羽飞 已提交
84
  virtual RC  find_cell(const TupleCellSpec &spec, TupleCell &cell) const = 0;
羽飞's avatar
羽飞 已提交
85

羽飞's avatar
羽飞 已提交
86
  virtual RC  cell_spec_at(int index, TupleCellSpec &spec) const = 0;
羽飞's avatar
羽飞 已提交
87
};
羽飞's avatar
羽飞 已提交
88

羽飞's avatar
羽飞 已提交
89 90 91 92 93 94 95
class RowTuple : public Tuple
{
public:
  RowTuple() = default;
  virtual ~RowTuple() = default;
  
  void set_record(Record *record)
96
  {
羽飞's avatar
羽飞 已提交
97
    this->record_ = record;
羽飞's avatar
羽飞 已提交
98 99
  }

羽飞's avatar
羽飞 已提交
100
  void set_table(Table *table)
101
  {
羽飞's avatar
羽飞 已提交
102
    this->table_ = table;
羽飞's avatar
羽飞 已提交
103 104
  }

羽飞's avatar
羽飞 已提交
105
  void set_schema(const std::vector<FieldMeta> *fields)
106
  {
羽飞's avatar
羽飞 已提交
107
    this->fields_ = fields;
羽飞's avatar
羽飞 已提交
108 109
  }

羽飞's avatar
羽飞 已提交
110
  int cell_num() const override
111
  {
羽飞's avatar
羽飞 已提交
112
    return fields_->size();
羽飞's avatar
羽飞 已提交
113 114
  }

羽飞's avatar
羽飞 已提交
115
  RC cell_at(int index, TupleCell &cell) const override
116
  {
羽飞's avatar
羽飞 已提交
117 118 119 120 121 122 123 124 125 126
    if (index < 0 || index >= fields_->size()) {
      LOG_WARN("invalid argument. index=%d", index);
      return RC::INVALID_ARGUMENT;
    }

    const FieldMeta &field_meta = (*fields_)[index];
    cell.set_table(table_);
    cell.set_type(field_meta.type());
    cell.set_data(this->record_->data() + field_meta.offset());
    return RC::SUCCESS;
羽飞's avatar
羽飞 已提交
127 128
  }

羽飞's avatar
羽飞 已提交
129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146
  RC find_cell(const TupleCellSpec &spec, TupleCell &cell) const override
  {
    const char *table_name = spec.table_name();
    if (0 != strcmp(table_name, table_->name())) {
      return RC::NOTFOUND;
    }

    const char *field_name = spec.field_name();
    for (int i = 0; i < fields_->size(); ++i) {
      const FieldMeta &field_meta = (*fields_)[i];
      if (0 == strcmp(field_name, field_meta.name())) {
	return cell_at(i, cell);
      }
    }
    return RC::NOTFOUND;
  }

  RC cell_spec_at(int index, TupleCellSpec &spec) const override
147
  {
羽飞's avatar
羽飞 已提交
148 149 150 151 152
    if (index < 0 || index >= fields_->size()) {
      LOG_WARN("invalid argument. index=%d", index);
      return RC::INVALID_ARGUMENT;
    }
    const FieldMeta &field_meta = (*fields_)[index];
羽飞's avatar
羽飞 已提交
153 154 155
    spec.set_table_name(table_->name());
    spec.set_field_name(field_meta.name());
    spec.set_alias(field_meta.name());
羽飞's avatar
羽飞 已提交
156
    return RC::SUCCESS;
羽飞's avatar
羽飞 已提交
157 158
  }

羽飞's avatar
羽飞 已提交
159
  Record &record()
160
  {
羽飞's avatar
羽飞 已提交
161
    return *record_;
羽飞's avatar
羽飞 已提交
162 163
  }

羽飞's avatar
羽飞 已提交
164
  const Record &record() const
165
  {
羽飞's avatar
羽飞 已提交
166
    return *record_;
羽飞's avatar
羽飞 已提交
167 168
  }
private:
羽飞's avatar
羽飞 已提交
169 170 171
  Record *record_ = nullptr;
  Table *table_ = nullptr;
  const std::vector<FieldMeta> *fields_ = nullptr;
羽飞's avatar
羽飞 已提交
172 173
};

羽飞's avatar
羽飞 已提交
174 175 176
/*
class CompositeTuple : public Tuple
{
羽飞's avatar
羽飞 已提交
177
public:
羽飞's avatar
羽飞 已提交
178 179
  int cell_num() const override; 
  RC  cell_at(int index, TupleCell &cell) const = 0;
羽飞's avatar
羽飞 已提交
180
private:
羽飞's avatar
羽飞 已提交
181
  int cell_num_ = 0;
羽飞's avatar
羽飞 已提交
182
  std::vector<Tuple *> tuples_;
羽飞's avatar
羽飞 已提交
183
};
羽飞's avatar
羽飞 已提交
184
*/
羽飞's avatar
羽飞 已提交
185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233

class ProjectTuple : public Tuple
{
public:
  ProjectTuple() = default;

  void set_tuple(Tuple *tuple)
  {
    this->tuple_ = tuple;
  }

  void add_cell_spec(const TupleCellSpec &spec)
  {
    speces_.push_back(spec);
  }
  int cell_num() const override
  {
    return speces_.size();
  }

  RC cell_at(int index, TupleCell &cell) const override
  {
    if (index < 0 || index >= speces_.size()) {
      return RC::GENERIC_ERROR;
    }
    if (tuple_ == nullptr) {
      return RC::GENERIC_ERROR;
    }

    const TupleCellSpec &spec = speces_[index]; // TODO better: add mapping between projection and raw tuple
    return tuple_->find_cell(spec, cell);
  }

  RC find_cell(const TupleCellSpec &spec, TupleCell &cell) const override
  {
    return tuple_->find_cell(spec, cell);
  }
  RC cell_spec_at(int index, TupleCellSpec &spec) const override
  {
    if (index < 0 || index >= speces_.size()) {
      return RC::NOTFOUND;
    }
    spec = speces_[index];
    return RC::SUCCESS;
  }
private:
  std::vector<TupleCellSpec> speces_;
  Tuple *tuple_ = nullptr;
};