/** * @brief create a rollback segment by selecting columns from a tuple * @param target_list The columns to be selected * @param tuple The tuple to construct the RB * * TODO: Optimization can be done. We can save copying those columns that are *already * in the rollback segment created by the same transaction. What we need to do *is to add * a bitmap in the rollback segment indicating columns it contains. After that *we * can bypass these columns when making a new rollback segment. */ RBSegType RollbackSegmentPool::CreateSegmentFromTuple( const catalog::Schema *schema, const TargetList &target_list, const AbstractTuple *tuple) { PL_ASSERT(schema); PL_ASSERT(target_list.size() != 0); size_t col_count = target_list.size(); size_t header_size = pairs_start_offset + col_count * sizeof(ColIdOffsetPair); size_t data_size = 0; RBSegType rb_seg = nullptr; // First figure out the total size of the rollback segment data area for (auto &target : target_list) { auto col_id = target.first; data_size += schema->GetLength(col_id); } // Allocate the RBSeg rb_seg = (RBSegType)pool_.AllocateZeroes(header_size + data_size); PL_ASSERT(rb_seg); // Fill in the header SetNextPtr(rb_seg, nullptr); SetTimeStamp(rb_seg, MAX_CID); SetColCount(rb_seg, col_count); // Fill in the col_id & offset pair and set the data field size_t offset = 0; for (size_t idx = 0; idx < target_list.size(); ++idx) { auto &target = target_list[idx]; auto col_id = target.first; const bool is_inlined = schema->IsInlined(col_id); const bool is_inbytes = false; size_t inline_col_size = schema->GetLength(col_id); size_t allocate_col_size = (is_inlined) ? inline_col_size : schema->GetVariableLength(col_id); SetColIdOffsetPair(rb_seg, idx, target.first, offset); // Set the value char *value_location = GetColDataLocation(rb_seg, idx); Value value = tuple->GetValue(col_id); PL_ASSERT(schema->GetType(col_id) == value.GetValueType()); value.SerializeToTupleStorageAllocateForObjects( value_location, is_inlined, allocate_col_size, is_inbytes, &pool_); // Update the offset offset += inline_col_size; } return rb_seg; }
void MagicMirror::Update(TargetList& targetList) { if (targetList.size() > 0) { Creature* target = targetList[rand() % targetList.size()]; if (target != this && target) { std::cout << m_name << " attacks " << target->GetName() << " with light beam...\n"; target->ApplyDamage(this, { 10 + rand() % m_bonusDamage, DamageType::RANGED, Element::FIRE }); } } }