Qual é a diferença entre os padrões Mapeador de Dados, Tabela Data Gateway (Gateway), Data Access Object (DAO) e Repository?

Estou tentando aprimorar minhas habilidades de padrão de design e estou curioso para saber quais são as diferenças entre esses padrões. Todos eles parecem ser a mesma coisa - encapsula a lógica do banco de dados para uma entidade específica, para que o código de chamada não tenha conhecimento da camada de persistência subjacente. De minha breve pesquisa, todos eles geralmente implementam seus métodos CRUD padrão e abstraem os detalhes específicos do banco de dado

Além das convenções de nomenclatura (por exemplo, CustomerMapper x CustomerDAO x CustomerGateway x CustomerRepository), qual é a diferença, se houver? Se houver uma diferença, quando você escolheria uma sobre a outra?

No passado, eu escrevia um código semelhante ao seguinte (simplificado, naturalmente - normalmente não usaria propriedades públicas):

public class Customer
{
    public long ID;
    public string FirstName;
    public string LastName;
    public string CompanyName;
}

public interface ICustomerGateway
{
    IList<Customer> GetAll();
    Customer GetCustomerByID(long id);
    bool AddNewCustomer(Customer customer);
    bool UpdateCustomer(Customer customer);
    bool DeleteCustomer(long id);
}

e ter umCustomerGateway classe que implementa a lógica específica do banco de dados para todos os métodos. Às vezes, eu não usava uma interface e tornava todos os métodos no CustomerGateway estáticos (eu sei, o que o torna menos testável) para que eu possa chamá-lo como:

Customer cust = CustomerGateway.GetCustomerByID(42);

Este parece ser o mesmo princípio para os padrões Data Mapper e Repository; o padrão DAO (que é a mesma coisa que Gateway, eu acho?) também parece incentivar gateways específicos do banco de dado

Estou esquecendo de algo? Parece um pouco estranho ter 3-4 maneiras diferentes de fazer a mesma cois

questionAnswers(5)

yourAnswerToTheQuestion