[c#] Can anonymous class implement interface?

Using Roslyn, you can dynamically create a class which inherits from an interface (or abstract class).

I use the following to create concrete classes from abstract classes.

In this example, AAnimal is an abstract class.

var personClass = typeof(AAnimal).CreateSubclass("Person");

Then you can instantiate some objects:

var person1 = Activator.CreateInstance(personClass);
var person2 = Activator.CreateInstance(personClass);

Without a doubt this won't work for every case, but it should be enough to get you started:

using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.CSharp;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Reflection;

namespace Publisher
{
    public static class Extensions
    {
        public static Type CreateSubclass(this Type baseType, string newClassName, string newNamespace = "Magic")
        {
            //todo: handle ref, out etc.
            var concreteMethods = baseType
                                    .GetMethods()
                                    .Where(method => method.IsAbstract)
                                    .Select(method =>
                                    {
                                        var parameters = method
                                                            .GetParameters()
                                                            .Select(param => $"{param.ParameterType.FullName} {param.Name}")
                                                            .ToString(", ");

                                        var returnTypeStr = method.ReturnParameter.ParameterType.Name;
                                        if (returnTypeStr.Equals("Void")) returnTypeStr = "void";

                                        var methodString = @$"
                                        public override {returnTypeStr} {method.Name}({parameters})
                                        {{
                                            Console.WriteLine(""{newNamespace}.{newClassName}.{method.Name}() was called"");
                                        }}";

                                        return methodString.Trim();
                                    })
                                    .ToList();

            var concreteMethodsString = concreteMethods
                                        .ToString(Environment.NewLine + Environment.NewLine);

            var classCode = @$"
            using System;

            namespace {newNamespace}
            {{
                public class {newClassName}: {baseType.FullName}
                {{
                    public {newClassName}()
                    {{
                    }}

                    {concreteMethodsString}
                }}
            }}
            ".Trim();

            classCode = FormatUsingRoslyn(classCode);


            /*
            var assemblies = new[]
            {
                MetadataReference.CreateFromFile(typeof(object).Assembly.Location),
                MetadataReference.CreateFromFile(baseType.Assembly.Location),
            };
            */

            var assemblies = AppDomain
                        .CurrentDomain
                        .GetAssemblies()
                        .Where(a => !string.IsNullOrEmpty(a.Location))
                        .Select(a => MetadataReference.CreateFromFile(a.Location))
                        .ToArray();

            var syntaxTree = CSharpSyntaxTree.ParseText(classCode);

            var compilation = CSharpCompilation
                                .Create(newNamespace)
                                .AddSyntaxTrees(syntaxTree)
                                .AddReferences(assemblies)
                                .WithOptions(new CSharpCompilationOptions(OutputKind.DynamicallyLinkedLibrary));

            using (var ms = new MemoryStream())
            {
                var result = compilation.Emit(ms);
                //compilation.Emit($"C:\\Temp\\{newNamespace}.dll");

                if (result.Success)
                {
                    ms.Seek(0, SeekOrigin.Begin);
                    Assembly assembly = Assembly.Load(ms.ToArray());

                    var newTypeFullName = $"{newNamespace}.{newClassName}";

                    var type = assembly.GetType(newTypeFullName);
                    return type;
                }
                else
                {
                    IEnumerable<Diagnostic> failures = result.Diagnostics.Where(diagnostic =>
                        diagnostic.IsWarningAsError ||
                        diagnostic.Severity == DiagnosticSeverity.Error);

                    foreach (Diagnostic diagnostic in failures)
                    {
                        Console.Error.WriteLine("{0}: {1}", diagnostic.Id, diagnostic.GetMessage());
                    }

                    return null;
                }
            }
        }

        public static string ToString(this IEnumerable<string> list, string separator)
        {
            string result = string.Join(separator, list);
            return result;
        }

        public static string FormatUsingRoslyn(string csCode)
        {
            var tree = CSharpSyntaxTree.ParseText(csCode);
            var root = tree.GetRoot().NormalizeWhitespace();
            var result = root.ToFullString();
            return result;
        }
    }
}