| 168 | } |
| 169 | |
| 170 | Result<const Kernel*> CastFunction::DispatchExact( |
| 171 | const std::vector<TypeHolder>& types) const { |
| 172 | RETURN_NOT_OK(CheckArity(types.size())); |
| 173 | |
| 174 | std::vector<const ScalarKernel*> candidate_kernels; |
| 175 | for (const auto& kernel : kernels_) { |
| 176 | if (kernel.signature->MatchesInputs(types)) { |
| 177 | candidate_kernels.push_back(&kernel); |
| 178 | } |
| 179 | } |
| 180 | |
| 181 | if (candidate_kernels.size() == 0) { |
| 182 | return Status::NotImplemented("Unsupported cast from ", types[0].type->ToString(), |
| 183 | " to ", ToTypeName(out_type_id_), " using function ", |
| 184 | this->name()); |
| 185 | } |
| 186 | |
| 187 | if (candidate_kernels.size() == 1) { |
| 188 | // One match, return it |
| 189 | return candidate_kernels[0]; |
| 190 | } |
| 191 | |
| 192 | // Now we are in a casting scenario where we may have both a EXACT_TYPE and |
| 193 | // a SAME_TYPE_ID. So we will see if there is an exact match among the |
| 194 | // candidate kernels and if not we will just return the first one |
| 195 | for (auto kernel : candidate_kernels) { |
| 196 | const InputType& arg0 = kernel->signature->in_types()[0]; |
| 197 | if (arg0.kind() == InputType::EXACT_TYPE) { |
| 198 | // Bingo. Return it |
| 199 | return kernel; |
| 200 | } |
| 201 | } |
| 202 | |
| 203 | // We didn't find an exact match. So just return some kernel that matches |
| 204 | return candidate_kernels[0]; |
| 205 | } |
| 206 | |
| 207 | Result<std::shared_ptr<CastFunction>> GetCastFunction(const DataType& to_type) { |
| 208 | internal::EnsureInitCastTable(); |