Generics and specialisation

I am not a big fan of inheritance. I would never say something like “inheritance is evil”, because inheritance, like composition, is just one of the many tools we can reach for, but in my experience, designs based on inheritance tend to be very rigid.

But here is one particular use case where I think the combination of generics and inheritance can provide an interesting solution.

As usual, the example that tries to illustrate this post is not very good. But it is close to my real use case, so I am going to stick with it.

I try to avoid boilerplate as much as possible. That’s why I try to use a generic implementation of the datasource protocols (UITableViewDataSource and UICollectionViewDataSource) to feed all my listings. I even released those datasources as a framework!

The thing is, there is always going to be some particular listing that does not fit completely into that framework. In particular, those listings that require implementing one of the optional methods.

For example, let’s take a look at tableView:titleForHeaderInSection. Do we need a header in every single tableview? Not really, some table views might not even be sectioned.

That method does not seem something that would belong in a generic datasource, because, well, it is there to provide a solution to a very specific use case.

So we could have a generic implementation of the UITableViewDatasource protocol like this (bear in mind I have over simplified it, for brevity):

class DataSource<T>: NSObject, UITableViewDataSource {
    let data: [T]
    init(data: [T]) { = data
    func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return data.count
    func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        return UITableViewCell()

struct Movie {
    let title: String

let movies = [Movie(title: "The Quiet Man"), Movie(title: "The Stagecoach") ]
let moviesDS = DataSource(data: movies)

struct Painter {
    let name: String

let painters = [Painter(name: "Picasso"), Painter(name: "Monet")]
let paintersDS = DataSource(data: painters)

This is generic enough to cover most of our use cases. But know, what if we need to provide a header for a very specific table?

Here is where subclassing to specialise can be handy. Let’s say our “special” listing is the one that displays Appliances. We could do something like this:

struct Appliance {
    let name: String

final class ApplianceDataSource: DataSource<Appliance> {
    func tableView(tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
        return "Hello, I'm your header"

And done. What is generic remains generic, what is specific to a particular data type remains encapsulated in one single class.

Of course, the next question would be “what happens if we want the specific case to apply to more than one type?”. Well, that would be a matter for a separate post…

Leave a Reply

Your email address will not be published. Required fields are marked *