Can I cast FScriptArray to TArray?

Is good this practice casting FScriptArray to TArray if I’m sure that UProperty has array defined as specified TArray template?

const FScriptArray& script_value = ArrayProp->GetPropertyValue_InContainer(StructData);
FScriptArray& v = const_cast<FScriptArray&>(script_value);
TArray<uint8>* value = reinterpret_cast<TArray<uint8>*>( &v );

TArray and FScriptArray are not interconnected by inheritance or something else. But has similar allocation in memory (as trick). Me right?

Hi,

TArray and FScriptArray are layout compatible, and are required as a basis for the property system. There is also FScriptMap, FScriptSet and FScriptSparseArray which are layout compatible with TMap, TSet and TSparseArray respectively.

However, while it’s always going to be the case that these FScript* classes have this compatibility, it’s generally not recommended to use them, as they are more an implementation detail of the UE4 reflection system. Correctly reading and manipulating elements within containers and honouring object lifetimes is considerably more involved than just casting to those classes and using them. What is your use case?

Steve

I can’t comment answers on my question, so I post comment as answer for you, Steve Robb.

My case is serialization exception where I serializing specific struct with TArray field.
I need to get this field as TArray:

// This struct is FMyStruct?
if (StructStructure->GetName() == GetNameSafe(FMyStruct::StaticStruct())
{
      // And then find field "Data" in this struct
      if ( UProperty* field = FindField<UProperty>(StructStructure, "Data") )
      {
           // This is TArray<uint8>, I need to cast to property value to TArray:
           const FScriptArray& script_value = field->GetPropertyValue_InContainer(StructData);
           ...
      }
}

If you absolutely know your field is a TArray<uint8>, then you can just cast to that as in your original post, without any problem.

If you want to be certain, you can add some extra checks:

UArrayProperty* field = FindField<UArrayProperty>(StructStructure, "Data");
if (field && field->Inner->IsA<UByteProperty>())
{
    const TArray<uint8>& byte_array = (const TArray<uint8>&)field->GetPropertyValue_InContainer(StructData);
}

Steve