dotnet/machinelearning · error · ArgumentException
type.RawType must be of type '{typeof(TValue).FullName}'.
Error message
type.RawType must be of type '{typeof(TValue).FullName}'. What it means
Builder.Add<TValue> enforces that the DataViewType's RawType equals typeof(TValue): the static generic parameter and the declared logical type must agree, otherwise the ValueGetter<TValue> would read the wrong CLR representation. Mismatch throws ArgumentException naming 'type'.
Source
Thrown at src/Microsoft.ML.DataView/DataViewSchema.cs:304
/// <summary>
/// Add one annotation column, strongly-typed version.
/// </summary>
/// <typeparam name="TValue">The type of the value.</typeparam>
/// <param name="name">The annotation name.</param>
/// <param name="type">The annotation type.</param>
/// <param name="getter">The getter delegate.</param>
/// <param name="annotations">Annotations of the input column. Note that annotations on an annotation column is somewhat rare
/// except for certain types (for example, slot names for a vector, key values for something of key type).</param>
public void Add<TValue>(string name, DataViewType type, ValueGetter<TValue> getter, Annotations annotations = null)
{
if (string.IsNullOrEmpty(name))
throw new ArgumentNullException(nameof(name));
if (type == null)
throw new ArgumentNullException(nameof(type));
if (getter == null)
throw new ArgumentNullException(nameof(getter));
if (type.RawType != typeof(TValue))
throw new ArgumentException($"{nameof(type)}.{nameof(type.RawType)} must be of type '{typeof(TValue).FullName}'.", nameof(type));
_items.Add((name, type, getter, annotations));
}
/// <summary>
/// Add one annotation column, weakly-typed version.
/// </summary>
/// <param name="name">The annotation name.</param>
/// <param name="type">The annotation type.</param>
/// <param name="getter">The getter delegate that provides the value. Note that the type of the getter is still checked
/// inside this method.</param>
/// <param name="annotations">Annotations of the input column. Note that annotations on an annotation column is somewhat rare
/// except for certain types (for example, slot names for a vector, key values for something of key type).</param>
public void Add(string name, DataViewType type, Delegate getter, Annotations annotations = null)
{
if (string.IsNullOrEmpty(name))
throw new ArgumentNullException(nameof(name));
if (type == null)View on GitHub (pinned to 7b76e69cf9)
Solutions
- Set TValue to exactly column.Type.RawType (or the well-known annotation type, e.g. VBuffer<ReadOnlyMemory<char>> for SlotNames)
- Derive the getter's generic type from the type first, then call the weakly-typed Add(name, type, Delegate) overload which marshals via MarshalActionInvoke
- Use AnnotationUtils/TypeUtils helpers that pick the correct TValue per DataViewType
Example fix
// before
builder.Add<VBuffer<float>>("SlotNames", NumberDataViewType.Single, getter);
// after
builder.Add<float>("SlotNames", NumberDataViewType.Single, getter); // TValue matches RawType
// or for vectors:
builder.Add<VBuffer<float>>("Features", new VectorDataViewType(NumberDataViewType.Single), getter); Defensive patterns
Strategy: type-guard
Validate before calling
if (type.RawType != typeof(TValue))
throw new InvalidOperationException($"Use TValue={type.RawType.Name} for type {type}");
builder.Add(name, type, getter); Type guard
bool TypeMatches<TValue>(DataViewType t) => t.RawType == typeof(TValue);
Try / catch
try { builder.Add<TValue>(name, type, getter); }
catch (ArgumentException e) when (e.ParamName == "type")
{
// fall back to weakly-typed dispatch
builder.Add(name, type, (Delegate)getter);
} Prevention
- Match TValue to type.RawType exactly; consult TypeUtils for annotation conventions (SlotNames => VBuffer<ReadOnlyMemory<char>>)
- For generic code, dispatch on RawType via MarshalActionInvoke instead of fixing TValue
- Verify key-type columns use their underlying raw type (e.g. uint) as TValue
When it happens
Trigger: Adding a column typed as VBuffer<float> while TValue is float[]; using NumberDataViewType.Double (RawType double) with a ValueGetter<float>; key types whose RawType is uint paired with an int getter.
Common situations: Generic helper code that fixes TValue at compile time but receives arbitrary DataViewTypes at runtime; copy-pasted annotation code (e.g. slot names use VBuffer<ReadOnlyMemory<char>>) adapted to scalar columns without changing TValue.
Understand the failure class
Background: Type mismatch errors: IllegalArgumentException, TypeError and type guards across 150 open-source libraries — this error's family across 150 libraries.
Related errors
- {DefaultColumnNames.Features} column must be of data type {N
- Invalid call to 'GetGetter'
- String.Format(Strings.MismatchedColumnValueType, this.DataTy
- Strings.BadColumnCast (formatted with column.DataType, typeo
- Strings.BadColumnCast (formatted with column.DataType, typeo
AI-assisted analysis of dotnet/machinelearning@7b76e69cf9 (2026-09-11).
Data as JSON: /api/errors/c0d503c7ae3c5c65.
Report an issue: GitHub.