reusing the same tests for different implementation

You could consider writing test classes as generic classes:

public abstract class IntervalFacts<T>
{
    [Theory, AutoCatalogData]
    public void MinimumIsCorrect(IComparable<T> first, 
        IComparable<T> second)
    {
        var sut = new Interval<T>(first, second);
        IComparable<T> result = sut.Minimum;
        Assert.Equal(result, first);
    }
}

public class DecimalIntervalFacts : IntervalFacts<decimal> { }
public class StringIntervalFacts : IntervalFacts<string> { }
public class DateTimeIntervalFacts : IntervalFacts<DateTime> { }
public class TimSpanIntervalFacts : IntervalFacts<TimeSpan> { }

This particular example takes advantage of AutoFixture's ability to compose concrete classes, which saves you the trouble of instantiating concrete instances of each T.

Varying the arrange phase is more difficult, but depending on what you need to do, again, you may be able to introduce some conventions to AutoFixture so that it automatically varies the created instances based on type.


For the types in the OP, you could write the tests like this:

public abstract class RepositoryFacts<T> where T : IRepository
{
    [Theory, AutoRepositoryData]
    public void GetRetrievesWhatWasPut(T sut)
    {
        sut.Set("key", 10);
        var result = sut.Get("key");
        result.Should().Be(10);
    }        
}

public class MemoryRepositoryFacts : RepositoryFacts<MemoryRepository> { }
public class FileReposityRepositoryFacts : RepositoryFacts<FileReposity> { }