Github user jorgebay commented on a diff in the pull request: https://github.com/apache/tinkerpop/pull/757#discussion_r153128066 --- Diff: gremlin-dotnet/src/Gremlin.Net/Process/Traversal/DefaultTraversal.cs --- @@ -86,9 +87,61 @@ public void Reset() } /// <inheritdoc /> - public E Current => (E)TraverserEnumerator.Current?.Object; + public E Current => GetCurrent<E>(); - object IEnumerator.Current => Current; + object IEnumerator.Current => GetCurrent(); + + private TReturn GetCurrent<TReturn>() + { + var value = GetCurrent(); + var returnType = typeof(TReturn); + if (value == null || value.GetType() == returnType) + { + // Avoid evaluating type comparisons + return (TReturn) value; + } + return (TReturn) GetValue(returnType, value); + } + + private object GetCurrent() + { + // Use dynamic to object to prevent runtime dynamic conversion evaluation + return TraverserEnumerator.Current?.Object; + } + + /// <summary> + /// Gets the value, converting to the expected type when necessary and supported. + /// </summary> + private static object GetValue(Type type, object value) + { + var genericType = type.GetTypeInfo().IsGenericType + ? type.GetTypeInfo().GetGenericTypeDefinition() + : null; + if (value is IDictionary dictValue && genericType == typeof(IDictionary<,>)) + { + var keyType = type.GenericTypeArguments[0]; + var valueType = type.GenericTypeArguments[1]; + var mapType = typeof(Dictionary<,>).MakeGenericType(keyType, valueType); + var result = (IDictionary) Activator.CreateInstance(mapType); + foreach (DictionaryEntry kv in dictValue) + { + result.Add(GetValue(keyType, kv.Key), GetValue(valueType, kv.Value)); + } + return result; + } + if (value is IEnumerable enumerableValue && genericType == typeof(IList<>)) --- End diff -- Its always easier to go from an strict API to a wider range of representations in the future than the other way around.
---