Good day. It has long been wondering how it is customary to store abstractions (interfaces, abstract classes) and their implementation relative to each other? In the same physical folder or in different? In one namespace or in different? Here are the possible options (Objects, Base - folders; IObject - interface; ConcreteObjectA and ConcreteObjectB - implementations of the IObject interface).

Option 1 - all in one folder and one namespace:

-> **Objects** -> IObject -> ConcreteObjectA -> ConcreteObjectB 

Option 2 - Base folder (or similar) for abstractions:

 -> **Objects** -> **Base** -> IObject -> ConcreteObjectA -> ConcreteObjectB 

Option 3 - Implementration folder (or similar) for implementations:

  -> **Objects** -> **Implementration** -> ConcreteObjectA -> ConcreteObjectB -> IObject 

Option 4 - your own (I will write in the answer).

Which option do you use? Why?

    2 answers 2

    The following option seems convenient to me:

    • The folder structure is equivalent to namespaces. That is, if the namespace of some class looks like ProjectName.Dynamic.Stubs , then this file must be located in the folder ProjectName\Dynamic\Stubs .

    • Interfaces and implementations are not distributed to individual namespaces, as long as their number in a given namespace seems reasonable.

    • In that case, if the number of interfaces in a single namespace begins to exceed 9-12 pieces, then they can be taken out into separate nested namespaces Interfaces. Implementations, respectively, are carried out in the name Implementation or Impl .

    • A real example in which the selection of individual namespaces for interfaces and their implementations is Rhino.Mocks.Interfaces and Rhino.Mocks.Impl .

    • A real example in which such a branch is not produced (which, by the way, did not damage readability ) is System.Linq, in which there are interfaces of the IQueryProvider type and their specific implementations of the EnumerableQuery<T> type EnumerableQuery<T> .

      It depends on the usage plan. Let's say you have an interface that (you are sure of it) will be used only within your project, then the place is next to the implementation.

      And if your interface / abstract class is planned to be used in other projects, then it is better to put it in a separate namespace / package / directory.

      The logic here is as follows: if reusability of the code is planned further, then your implementation / implementation of abstractions will probably not be very interesting to the potential consumer, respectively, he (a) will take / import only the abstractions themselves.

      Example: a java.sql package that contains abstraction declarations for working through JDBC, and their specific implementation is always contained separately and is usually provided by the JDBC driver. For example, for Oracle, the oracle.jdbc package looks like this