浏览代码

Align delegates with .NET 3.5

Jon Skeet 17 年之前
父节点
当前提交
b01135c485

+ 7 - 9
csharp/ProtocolBuffers/FieldAccess/Delegates.cs

@@ -16,13 +16,11 @@
 
 namespace Google.ProtocolBuffers.FieldAccess {
 
-  // TODO(jonskeet): Convert these to Func/Action family
-  delegate bool HasDelegate<T>(T message);
-  delegate T ClearDelegate<T>(T builder);
-  delegate int RepeatedCountDelegate<T>(T message);
-  delegate object GetValueDelegate<T>(T message);
-  delegate void SingleValueDelegate<TSource>(TSource source, object value);
-  delegate IBuilder CreateBuilderDelegate();
-  delegate object GetIndexedValueDelegate<T>(T message, int index);
-  delegate object SetIndexedValueDelegate<T>(T message, int index, object value);
+  // These delegate declarations mirror the ones in .NET 3.5 for the sake of familiarity.
+  internal delegate TResult Func<TResult>();
+  internal delegate TResult Func<T, TResult>(T arg);
+  internal delegate TResult Func<T1, T2, TResult>(T1 arg1, T2 arg2);
+  internal delegate TResult Func<T1, T2, T3, TResult>(T1 arg1, T2 arg2, T3 arg3);
+  internal delegate TResult Func<T1, T2, T3, T4, TResult>(T1 arg1, T2 arg2, T3 arg3, T4 arg4); 
+  internal delegate void Action<T1, T2>(T1 arg1, T2 arg2);
 }

+ 17 - 26
csharp/ProtocolBuffers/FieldAccess/ReflectionUtil.cs

@@ -32,25 +32,23 @@ namespace Google.ProtocolBuffers.FieldAccess {
     /// Creates a delegate which will execute the given method and then return
     /// the result as an object.
     /// </summary>
-    public static GetValueDelegate<T> CreateUpcastDelegate<T>(MethodInfo method) {
+    public static Func<T, object> CreateUpcastDelegate<T>(MethodInfo method) {
 
       // The tricky bit is invoking CreateCreateUpcastDelegateImpl with the right type parameters
       MethodInfo openImpl = typeof(ReflectionUtil).GetMethod("CreateUpcastDelegateImpl");
       MethodInfo closedImpl = openImpl.MakeGenericMethod(typeof(T), method.ReturnType);
-      return (GetValueDelegate<T>) closedImpl.Invoke(null, new object[] { method });
+      return (Func<T, object>) closedImpl.Invoke(null, new object[] { method });
     }
 
-    delegate TResult Getter<TSource, TResult>(TSource source);
-
     /// <summary>
     /// Method used solely for implementing CreateUpcastDelegate. Public to avoid trust issues
     /// in low-trust scenarios, e.g. Silverlight.
     /// TODO(jonskeet): Check any of this actually works in Silverlight...
     /// </summary>
-    public static GetValueDelegate<TSource> CreateUpcastDelegateImpl<TSource, TResult>(MethodInfo method) {
+    public static Func<TSource, object> CreateUpcastDelegateImpl<TSource, TResult>(MethodInfo method) {
       // Convert the reflection call into an open delegate, i.e. instead of calling x.Method()
       // we'll call getter(x).
-      Getter<TSource, TResult> getter = (Getter<TSource, TResult>)Delegate.CreateDelegate(typeof(Getter<TSource, TResult>), method);
+      Func<TSource, TResult> getter = (Func<TSource, TResult>)Delegate.CreateDelegate(typeof(Func<TSource, TResult>), method);
 
       // Implicit upcast to object (within the delegate)
       return delegate(TSource source) { return getter(source); };
@@ -61,19 +59,16 @@ namespace Google.ProtocolBuffers.FieldAccess {
     /// Creates a delegate which will execute the given method after casting the parameter
     /// down from object to the required parameter type.
     /// </summary>
-    public static SingleValueDelegate<T> CreateDowncastDelegate<T>(MethodInfo method) {
+    public static Action<T, object> CreateDowncastDelegate<T>(MethodInfo method) {
       MethodInfo openImpl = typeof(ReflectionUtil).GetMethod("CreateDowncastDelegateImpl");
       MethodInfo closedImpl = openImpl.MakeGenericMethod(typeof(T), method.GetParameters()[0].ParameterType);
-      return (SingleValueDelegate<T>)closedImpl.Invoke(null, new object[] { method });
+      return (Action<T, object>) closedImpl.Invoke(null, new object[] { method });
     }
 
-    delegate void OpenSingleValueDelegate<TSource, TParam>(TSource source, TParam parameter);
-
-    public static SingleValueDelegate<TSource> CreateDowncastDelegateImpl<TSource, TParam>(MethodInfo method) {
+    public static Action<TSource, object> CreateDowncastDelegateImpl<TSource, TParam>(MethodInfo method) {
       // Convert the reflection call into an open delegate, i.e. instead of calling x.Method(y) we'll
       // call Method(x, y)
-      OpenSingleValueDelegate<TSource, TParam> call = (OpenSingleValueDelegate<TSource, TParam>)
-          Delegate.CreateDelegate(typeof(OpenSingleValueDelegate<TSource, TParam>), method);
+      Action<TSource, TParam> call = (Action<TSource, TParam>) Delegate.CreateDelegate(typeof(Action<TSource, TParam>), method);
 
       return delegate(TSource source, object parameter) { call(source, (TParam)parameter); };
     }
@@ -82,36 +77,32 @@ namespace Google.ProtocolBuffers.FieldAccess {
     /// Creates a delegate which will execute the given method after casting the parameter
     /// down from object to the required parameter type.
     /// </summary>
-    public static SingleValueDelegate<T> CreateDowncastDelegateIgnoringReturn<T>(MethodInfo method) {
+    public static Action<T, object> CreateDowncastDelegateIgnoringReturn<T>(MethodInfo method) {
       MethodInfo openImpl = typeof(ReflectionUtil).GetMethod("CreateDowncastDelegateIgnoringReturnImpl");
       MethodInfo closedImpl = openImpl.MakeGenericMethod(typeof(T), method.GetParameters()[0].ParameterType, method.ReturnType);
-      return (SingleValueDelegate<T>)closedImpl.Invoke(null, new object[] { method });
+      return (Action<T, object>)closedImpl.Invoke(null, new object[] { method });
     }
 
-    delegate TReturn OpenSingleValueDelegate<TSource, TParam, TReturn>(TSource source, TParam parameter);
-
-    public static SingleValueDelegate<TSource> CreateDowncastDelegateIgnoringReturnImpl<TSource, TParam, TReturn>(MethodInfo method) {
+    public static Action<TSource, object> CreateDowncastDelegateIgnoringReturnImpl<TSource, TParam, TReturn>(MethodInfo method) {
       // Convert the reflection call into an open delegate, i.e. instead of calling x.Method(y) we'll
       // call Method(x, y)
-      OpenSingleValueDelegate<TSource, TParam, TReturn> call = (OpenSingleValueDelegate<TSource, TParam, TReturn>)
-          Delegate.CreateDelegate(typeof(OpenSingleValueDelegate<TSource, TParam, TReturn>), method);
+      Func<TSource, TParam, TReturn> call = (Func<TSource, TParam, TReturn>)
+          Delegate.CreateDelegate(typeof(Func<TSource, TParam, TReturn>), method);
 
       return delegate(TSource source, object parameter) { call(source, (TParam)parameter); };
     }
 
-    delegate T OpenCreateBuilderDelegate<T>();
-
     /// <summary>
     /// Creates a delegate which will execute the given static method and cast the result up to IBuilder.
     /// </summary>
-    public static CreateBuilderDelegate CreateStaticUpcastDelegate(MethodInfo method) {
+    public static Func<IBuilder> CreateStaticUpcastDelegate(MethodInfo method) {
       MethodInfo openImpl = typeof(ReflectionUtil).GetMethod("CreateStaticUpcastDelegateImpl");
       MethodInfo closedImpl = openImpl.MakeGenericMethod(method.ReturnType);
-      return (CreateBuilderDelegate) closedImpl.Invoke(null, new object[] { method });
+      return (Func<IBuilder>)closedImpl.Invoke(null, new object[] { method });
     }
 
-    public static CreateBuilderDelegate CreateStaticUpcastDelegateImpl<T>(MethodInfo method) {
-      OpenCreateBuilderDelegate<T> call = (OpenCreateBuilderDelegate<T>)Delegate.CreateDelegate(typeof(OpenCreateBuilderDelegate<T>), method);
+    public static Func<IBuilder> CreateStaticUpcastDelegateImpl<T>(MethodInfo method) {
+      Func<T> call = (Func<T>)Delegate.CreateDelegate(typeof(Func<T>), method);
       return delegate { return (IBuilder)call(); };
     }
   }

+ 1 - 1
csharp/ProtocolBuffers/FieldAccess/RepeatedMessageAccessor.cs

@@ -33,7 +33,7 @@ namespace Google.ProtocolBuffers.FieldAccess {
     /// in a message type "Foo", a field called "bar" might be of type "Baz". This
     /// method is Baz.CreateBuilder.
     /// </summary>
-    private readonly CreateBuilderDelegate createBuilderDelegate;
+    private readonly Func<IBuilder> createBuilderDelegate;
 
     internal RepeatedMessageAccessor(string name) : base(name) {
       MethodInfo createBuilderMethod = ClrType.GetMethod("CreateBuilder", new Type[0]);

+ 8 - 8
csharp/ProtocolBuffers/FieldAccess/RepeatedPrimitiveAccessor.cs

@@ -26,11 +26,11 @@ namespace Google.ProtocolBuffers.FieldAccess {
       where TBuilder : IBuilder<TMessage, TBuilder> {
 
     private readonly Type clrType;
-    private readonly GetValueDelegate<TMessage> getValueDelegate;
-    private readonly ClearDelegate<TBuilder> clearDelegate;
-    private readonly SingleValueDelegate<TBuilder> addValueDelegate;
-    private readonly GetValueDelegate<TBuilder> getRepeatedWrapperDelegate;
-    private readonly RepeatedCountDelegate<TMessage> countDelegate;
+    private readonly Func<TMessage, object> getValueDelegate;
+    private readonly Func<TBuilder, IBuilder> clearDelegate;
+    private readonly Action<TBuilder, object> addValueDelegate;
+    private readonly Func<TBuilder, object> getRepeatedWrapperDelegate;
+    private readonly Func<TMessage, int> countDelegate;
     private readonly MethodInfo getElementMethod;
     private readonly MethodInfo setElementMethod;
     
@@ -62,9 +62,9 @@ namespace Google.ProtocolBuffers.FieldAccess {
           || setElementMethod == null) {
         throw new ArgumentException("Not all required properties/methods available");
       }
-      clearDelegate = (ClearDelegate<TBuilder>)Delegate.CreateDelegate(typeof(ClearDelegate<TBuilder>), clearMethod);
-      countDelegate = (RepeatedCountDelegate<TMessage>)Delegate.CreateDelegate
-          (typeof(RepeatedCountDelegate<TMessage>), countProperty.GetGetMethod());
+      clearDelegate = (Func<TBuilder, IBuilder>)Delegate.CreateDelegate(typeof(Func<TBuilder, IBuilder>), clearMethod);
+      countDelegate = (Func<TMessage, int>)Delegate.CreateDelegate
+          (typeof(Func<TMessage, int>), countProperty.GetGetMethod());
       getValueDelegate = ReflectionUtil.CreateUpcastDelegate<TMessage>(messageProperty.GetGetMethod());
       addValueDelegate = ReflectionUtil.CreateDowncastDelegateIgnoringReturn<TBuilder>(addMethod);
       getRepeatedWrapperDelegate = ReflectionUtil.CreateUpcastDelegate<TBuilder>(builderProperty.GetGetMethod());

+ 1 - 1
csharp/ProtocolBuffers/FieldAccess/SingleMessageAccessor.cs

@@ -29,7 +29,7 @@ namespace Google.ProtocolBuffers.FieldAccess {
     /// in a message type "Foo", a field called "bar" might be of type "Baz". This
     /// method is Baz.CreateBuilder.
     /// </summary>
-    private readonly CreateBuilderDelegate createBuilderDelegate;
+    private readonly Func<IBuilder> createBuilderDelegate;
 
     internal SingleMessageAccessor(string name) : base(name) {      
       MethodInfo createBuilderMethod = ClrType.GetMethod("CreateBuilder", new Type[0]);

+ 7 - 6
csharp/ProtocolBuffers/FieldAccess/SinglePrimitiveAccessor.cs

@@ -25,10 +25,11 @@ namespace Google.ProtocolBuffers.FieldAccess {
       where TBuilder : IBuilder<TMessage, TBuilder> {
 
     private readonly Type clrType;
-    private readonly GetValueDelegate<TMessage> getValueDelegate;
-    private readonly SingleValueDelegate<TBuilder> setValueDelegate;
-    private readonly HasDelegate<TMessage> hasDelegate;
-    private readonly ClearDelegate<TBuilder> clearDelegate;
+    private readonly Func<TMessage, object> getValueDelegate;
+    private readonly Action<TBuilder, object> setValueDelegate;
+    private readonly Func<TMessage, bool> hasDelegate;
+    private readonly Func<TBuilder, IBuilder> clearDelegate;
+    delegate void SingleValueDelegate<TSource>(TSource source, object value);
 
     /// <summary>
     /// The CLR type of the field (int, the enum type, ByteString, the message etc).
@@ -47,8 +48,8 @@ namespace Google.ProtocolBuffers.FieldAccess {
         throw new ArgumentException("Not all required properties/methods available");
       }
       clrType = messageProperty.PropertyType;
-      hasDelegate = (HasDelegate<TMessage>)Delegate.CreateDelegate(typeof(HasDelegate<TMessage>), hasProperty.GetGetMethod());
-      clearDelegate = (ClearDelegate<TBuilder>)Delegate.CreateDelegate(typeof(ClearDelegate<TBuilder>), clearMethod);
+      hasDelegate = (Func<TMessage, bool>)Delegate.CreateDelegate(typeof(Func<TMessage, bool>), hasProperty.GetGetMethod());
+      clearDelegate = (Func<TBuilder, IBuilder>)Delegate.CreateDelegate(typeof(Func<TBuilder, IBuilder>), clearMethod);
       getValueDelegate = ReflectionUtil.CreateUpcastDelegate<TMessage>(messageProperty.GetGetMethod());
       setValueDelegate = ReflectionUtil.CreateDowncastDelegate<TBuilder>(builderProperty.GetSetMethod());
     }