Problems creating a PipelineRegressor from a PyTorch converted model

I am trying to create a Pipeline with 3 sub-models: a Feature Vectorizer -> a NN regressor converted from PyTorch -> a Feature Extractor (to convert the output tensor to a Double value).

The pipeline works fine when I use just a Vectorizer and an Extractor, this is the code:


vectorizer = models.feature_vectorizer.create_feature_vectorizer(
    input_features=["windSpeed", "theoreticalPowerCurve", "windDirection"],  # Multiple input features
    output_feature_name="input"
)

preProc_spec = vectorizer[0]

ct.utils.convert_double_to_float_multiarray_type(preProc_spec)

extractor = models.array_feature_extractor.create_array_feature_extractor(
    input_features=[("input",datatypes.Array(3,))],  # Multiple input features
    output_name="output",
    extract_indices = 1
)

ct.utils.convert_double_to_float_multiarray_type(extractor)

pipeline_network = pipeline.PipelineRegressor (
   input_features = ["windSpeed", "theoreticalPowerCurve", "windDirection"],
   output_features=["output"]
)

pipeline_network.add_model(preProc_spec)

pipeline_network.add_model(extractor)

ct.utils.convert_double_to_float_multiarray_type(pipeline_network.spec)

ct.utils.save_spec(pipeline_network.spec,"Final.mlpackage")

This model works ok. I created a regression NN using PyTorch and converted to Core ML either

import torch
import torch.nn as nn

class TurbinePowerModel(nn.Module):
  def __init__(self):
    super().__init__()
    self.linear1 = nn.Linear(3, 4)
    self.activation1 = nn.ReLU()
    #self.linear2 = nn.Linear(5, 4)
    #self.activation2 = nn.ReLU()
    self.output = nn.Linear(4, 1)



  def forward(self, x):
    #x = F.normalize(x, dim = 0)
    x = self.linear1(x)
    x = self.activation1(x)
   # x = self.linear2(x)
   # x = self.activation2(x)
    x = self.output(x)
    return x

  def forward_inference(self, windSpeed,theoreticalPowerCurve,windDirection):
     input_tensor = torch.tensor([windSpeed,
                                  theoreticalPowerCurve,
                                  windDirection], dtype=torch.float32)

     return self.forward(input_tensor)

model = torch.load('TurbinePowerRegression-1layer.pt', weights_only=False)

import coremltools as ct

print(ct.__version__)

import pandas as pd
from sklearn.preprocessing import StandardScaler

df = pd.read_csv('T1_clean.csv',delimiter=';')

X = df[['WindSpeed','TheoreticalPowerCurve','WindDirection']]
y = df[['ActivePower']]

scaler = StandardScaler()
X = scaler.fit_transform(X)
y = scaler.fit_transform(y)

X_tensor = torch.tensor(X, dtype=torch.float32)
y_tensor = torch.tensor(y, dtype=torch.float32)

traced_model = torch.jit.trace(model, X_tensor[0])

mlmodel = ct.convert(
    traced_model,
    inputs=[ct.TensorType(name="input", shape=X_tensor[0].shape)],
    classifier_config=None  # Optional, for classification tasks
)

mlmodel.save("TurbineBase.mlpackage")

This model has a Multiarray(Float 32 3) as input and a Multiarray(Float32 1) as output.

When I try to include it in the middle of the pipeline (Adjusting the output and input types of the other models accordingly), the process runs ok, but I have the following error when opening the generated model on Xcode:

What's is missing on the models. How can I set or adjust this metadata properly?

Thanks!!!

Problems creating a PipelineRegressor from a PyTorch converted model
 
 
Q