<commit_before>﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using Ploeh.AutoFixture.Kernel;

namespace Ploeh.AutoFixture.AutoNSubstitute
{
    internal class GenericStaticMethod : IMethod
    {
        private readonly MethodInfo methodInfo;
        private readonly ParameterInfo[] parameters;

        public GenericStaticMethod(MethodInfo methodInfo)
        {
            if (methodInfo == null)
                throw new ArgumentNullException("methodInfo");

            this.methodInfo = methodInfo;
            this.parameters = methodInfo.GetParameters();
        }

        public IEnumerable<ParameterInfo> Parameters
        {
            get { return this.parameters; }
        }

        public MethodInfo MethodInfo
        {
            get { return methodInfo; }
        }

        private static IEnumerable<Tuple<Type, Type>> Resolve(Type argument, Type parameter)
        {
            if (parameter.IsGenericParameter)
                return new[] { Tuple.Create(parameter, argument) };

            if (argument.HasElementType)
                return Resolve(argument.GetElementType(), parameter.GetElementType());

            return argument.GetGenericArguments()
                .Zip(parameter.GetGenericArguments(), Resolve)
                .SelectMany(x => x);
        }

        private static MethodInfo InferMethodInfo(MethodInfo methodInfo, IEnumerable<object> arguments)
        {
            if (methodInfo.ContainsGenericParameters)
            {
                var typeMap = arguments.Zip(methodInfo.GetParameters(),
                    (argument, parameter) => Resolve(GetType(argument), parameter.ParameterType))
                    .SelectMany(x => x)
                    .ToLookup(x => x.Item1, x => x.Item2);

                var actuals = methodInfo.GetGenericArguments()
                    .Select(x => typeMap[x].Aggregate((t1, t2) => t1.IsAssignableFrom(t2) ? t2 : t1));

                return methodInfo.MakeGenericMethod(actuals.ToArray());
            }

            return methodInfo;
        }

        private static Type GetType(object argument)
        {
            return argument == null ? typeof(object) : argument.GetType();
        }

        public object Invoke(IEnumerable<object> arguments)
        {
            var args = arguments.ToArray();
            return InferMethodInfo(MethodInfo, args)
                .Invoke(null, args);
        }<commit_msg>renamed Resolve to ResolveGenericType<commit_after>﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using Ploeh.AutoFixture.Kernel;

namespace Ploeh.AutoFixture.AutoNSubstitute
{
    internal class GenericStaticMethod : IMethod
    {
        private readonly MethodInfo methodInfo;
        private readonly ParameterInfo[] parameters;

        public GenericStaticMethod(MethodInfo methodInfo)
        {
            if (methodInfo == null)
                throw new ArgumentNullException("methodInfo");

            this.methodInfo = methodInfo;
            this.parameters = methodInfo.GetParameters();
        }

        public IEnumerable<ParameterInfo> Parameters
        {
            get { return this.parameters; }
        }

        public MethodInfo MethodInfo
        {
            get { return methodInfo; }
        }

        private static IEnumerable<Tuple<Type, Type>> ResolveGenericType(Type argument, Type parameter)
        {
            if (parameter.IsGenericParameter)
                return new[] { Tuple.Create(parameter, argument) };

            if (argument.HasElementType)
                return ResolveGenericType(argument.GetElementType(), parameter.GetElementType());

            return argument.GetGenericArguments()
                .Zip(parameter.GetGenericArguments(), ResolveGenericType)
                .SelectMany(x => x);
        }

        private static MethodInfo InferMethodInfo(MethodInfo methodInfo, IEnumerable<object> arguments)
        {
            if (methodInfo.ContainsGenericParameters)
            {
                var typeMap = arguments.Zip(methodInfo.GetParameters(),
                    (argument, parameter) => ResolveGenericType(GetType(argument), parameter.ParameterType))
                    .SelectMany(x => x)
                    .ToLookup(x => x.Item1, x => x.Item2);

                var actuals = methodInfo.GetGenericArguments()
                    .Select(x => typeMap[x].Aggregate((t1, t2) => t1.IsAssignableFrom(t2) ? t2 : t1));

                return methodInfo.MakeGenericMethod(actuals.ToArray());
            }

            return methodInfo;
        }

        private static Type GetType(object argument)
        {
            return argument == null ? typeof(object) : argument.GetType();
        }

        public object Invoke(IEnumerable<object> arguments)
        {
            var args = arguments.ToArray();
            return InferMethodInfo(MethodInfo, args)
                .Invoke(null, args);
        }
{'fraction_non_alphanumeric': 0.08925029750099167, 'fraction_numerical': 0.0031733439111463705, 'mean_word_length': 2.0526634382566584, 'pattern_counts': {'":': 0, '<': 13, '<?xml version=': 0, '>': 27, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '921174', 'n_tokens_mistral': 1265, 'n_tokens_neox': 1209, 'n_words': 269}