| 201 | } |
| 202 | |
| 203 | inline static void InferLabelShape( |
| 204 | const std::vector<std::string>& op_labels, |
| 205 | const std::vector<DDim>& inputs, |
| 206 | LabelMap* labelshape, |
| 207 | std::vector<std::vector<int64_t>>* broadcast_shapes, |
| 208 | LabelMap* labeltype) { |
| 209 | LabelMap labelshape_copy = *labelshape; |
| 210 | VLOG(5) << "Start InferLabelShape"; |
| 211 | for (size_t i = 0; i < op_labels.size(); ++i) { |
| 212 | auto& op_str = op_labels[i]; |
| 213 | auto& op_dim = inputs[i]; |
| 214 | VLOG(5) << "i = " << i << " op_str " << op_str << " op_dim " << op_dim; |
| 215 | int dim_ptr = 0; |
| 216 | for (auto& c : op_str) { |
| 217 | if (!labelshape->exist(c) || abs((*labelshape)[c]) == 1) { |
| 218 | VLOG(5) |
| 219 | << "if (!labelshape->exist(c) || abs((*labelshape)[c]) == 1) c = " |
| 220 | << c << " (*labelshape)[c] " << (*labelshape)[c] |
| 221 | << " op_dim[dim_ptr] " << op_dim[dim_ptr]; |
| 222 | (*labelshape)[c] = static_cast<int>(op_dim[dim_ptr]); |
| 223 | } else if (abs(op_dim[dim_ptr]) != 1) { |
| 224 | VLOG(5) << "if (abs(op_dim[dim_ptr]) != 1) c = " << c |
| 225 | << " (*labelshape)[c] " << (*labelshape)[c] |
| 226 | << " op_dim[dim_ptr] " << op_dim[dim_ptr]; |
| 227 | PADDLE_ENFORCE_EQ( |
| 228 | (*labelshape)[c], |
| 229 | op_dim[dim_ptr], |
| 230 | common::errors::InvalidArgument( |
| 231 | "Same label have different shapes for label: `%c`", c)); |
| 232 | } |
| 233 | dim_ptr++; |
| 234 | } |
| 235 | } |
| 236 | for (size_t i = 0; i < op_labels.size(); ++i) { |
| 237 | for (auto& c : op_labels[i]) { |
| 238 | // Note: When broadcasting is involved, ensure the gradient is calculated |
| 239 | // with respect to the broadcasted shape. For example, in |
| 240 | // einsum("ij,ij->j", x(2,2), y(1,2)), y is broadcast to (2,2). The |
| 241 | // gradient calculation for x must use this broadcasted shape of y. |
| 242 | if (labelshape_copy.exist(c) && labelshape_copy[c] > (*labelshape)[c]) { |
| 243 | // Strict check for the situation. |
| 244 | PADDLE_ENFORCE_EQ( |
| 245 | (*labelshape)[c] == 1 && ((*labeltype)[c] == LabelType::AO || |
| 246 | (*labeltype)[c] == LabelType::BO), |
| 247 | true, |
| 248 | common::errors::InvalidArgument( |
| 249 | "Broadcast dims must be 1 for label: `%c`", c)); |
| 250 | (*labelshape)[c] = labelshape_copy[c]; |
| 251 | } |
| 252 | (*broadcast_shapes)[i].push_back((*labelshape)[c]); |
| 253 | } |
| 254 | } |
| 255 | for (size_t i = 0; i < op_labels.size(); ++i) { |
| 256 | VLOG(5) << "InferLabelShape: After broadcast shape is:" |
| 257 | << paddle::string::join_strings((*broadcast_shapes)[i], ","); |
| 258 | } |
| 259 | } |
| 260 |
no test coverage detected