Why general inheritance is flawed and how to finally fix it
I (happily) write a lot of OOP code, &quot;inheritance is bad, use composition&quot; is such a trite and unhelpful dogma that gets in the way of any actual discussion about where inheritance is useful.<p>IMO, the case where inheritance makes the most sense is when you have a set of objects polymorphically answering some question, usually with a <i>simple</i> answer.<p><pre><code>    class Subset
        class Whole &lt; Subset
            def of(items)
                items
            end
        end

        class Range &lt; Subset
            def initialize(from:, to:)
                @from = from
                @to   = to
            end

            def of(items)
                items[@from:@to]
            end
        end
    end
</code></pre>
which is used as such:<p><pre><code>    subset = Subset::Whole.new
    puts subset.of([&quot;a&quot;, &quot;b&quot;, &quot;c&quot;]) # =&gt; [&quot;a&quot;, &quot;b&quot;, &quot;c&quot;]

    subset = Subset::Range.new(from: 0, to: 1)
    puts subset.of([&quot;a&quot;, &quot;b&quot;, &quot;c&quot;]) # =&gt; [&quot;a&quot;]
</code></pre>
You can then pass around a Subset object anywhere (aka dependency injection) and push conditionals up the stack as far as possible.<p>Simply saying &quot;inheritance is bad&quot; gets nobody anywhere.