# Why is it impossible to subtype a struct?

**URL:** <https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876>\
**Category:** General Usage\
**Created:** [January 21, 2019, 2:56pm UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876 "2019-01-21T14:56:38Z")\
**Posts on this page:** 20\
**Page:** 1

<div class="post-metadata">

**Author:** ![gdkrmr](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdkrmr/32/2791_2.png) [@gdkrmr](https://discourse.julialang.org/u/gdkrmr)\
**Post date:** [January 21, 2019, 2:56pm UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/1 "2019-01-21T14:56:38Z")

</div>

Is there a deeper reason, why the following does not work? I guess a `struct` can only be a leaf in the type hierarchy. Is there a reason why this has to be like this?

```julia
julia> struct TypeA{T} 
           data::T 
       end

julia> struct TypeB{T} <: TypeA{T} 
           data::T 
       end
ERROR: invalid subtyping in definition of TypeB

```

Edit, I found the follwing in the [Manual](https://docs.julialang.org/en/v1/manual/types/):

> One particularly distinctive feature of Julia’s type system is that concrete types may not subtype each other: all concrete types are final and may only have abstract types as their supertypes.

---

<div class="post-metadata">

**Author:** ![StefanKarpinski](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stefankarpinski/32/24_2.png) [@StefanKarpinski](https://discourse.julialang.org/u/StefanKarpinski)\
**Post date:** [January 21, 2019, 3:39pm UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/3 "2019-01-21T15:39:56Z")

</div>

Multiple inheritance is a totally different story and could be allowed. I’ve written about why we don’t allow subtyping of concrete types before if someone wants to dig up one of my earlier posts about it.

Edit: here’s a link to an old google groups conversation about it

[https://groups.google.com/d/msg/julia-dev/eA4VkFAD-yQ/LNUP\_OT0zy0J](https://groups.google.com/d/msg/julia-dev/eA4VkFAD-yQ/LNUP_OT0zy0J)

In particular, this paragraph from the end of my first post on the thread sums up my position fairly well still:

> While there are a number of practical reasons to disallow subtyping of concrete types, I think they all stem from the basic fact that subtyping a concrete type is logically unsound. A type can only be instantiated if it is _completely_ specified, and it only makes sense to subtype something if it is _incompletely_ specified. Thus, a type should either be abstract or concrete but not both. What object-oriented languages that allow the same type to be both instantiated and subtyped are really doing is using the same name for two different things: a concrete type that can be instantiated and an abstract type that can be subtyped. Problems ensue since there’s no way to express which you mean. You end up with attempts to resolve this confusion like the “final” keyword and recommendations against ever subtyping classes that weren’t intended to be abstract. But wouldn’t it be better not to conflate the two things in the first place?

---

<div class="post-metadata">

**Author:** ![stevengj](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stevengj/32/71_2.png) [@stevengj](https://discourse.julialang.org/u/stevengj)\
**Post date:** [January 21, 2019, 3:57pm UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/4 "2019-01-21T15:57:03Z")

</div>

Note that if what you really want is the ability to declare fields in an abstract type, that is not a crazy idea:

[https://github.com/JuliaLang/julia/issues/4935](https://github.com/JuliaLang/julia/issues/4935)

Although it was proposed a long time ago, and has support in principle from several core developers, no one seems to have made it a high priority to implement, probably because most Julia programmers don’t find themselves needing this feature often once they shake off old OOP habits.

---

<div class="post-metadata">

**Author:** ![StefanKarpinski](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/stefankarpinski/32/24_2.png) [@StefanKarpinski](https://discourse.julialang.org/u/StefanKarpinski)\
**Post date:** [January 21, 2019, 4:25pm UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/5 "2019-01-21T16:25:03Z")

</div>

I think the main lack of enthusiasm came (for me at least) at [this point](https://github.com/JuliaLang/julia/issues/4935#issuecomment-31874142) in the conversation. Reading that comment it’s a little hard to parse quite what I’m getting at but let me try to explain it more clearly. The crux of the question is what would doing this mean:

```julia
abstract type Rectangle{T<:Real}
    width::T
    height::T
end

```

Does it mean that every subtype of `Rectangle ` must have actual fields `width` and `height` of type `T` ? Naively that’s what one would think. But then what if you want to declare `Square <: Rectangle` with a single `side::T` field but which provides `getproperty` implementations of `width` and `height`? It seems like the naive meaning of declaring fields on an abstract type would prevent that, or at least force you to store both the width and the height even though you actually only want `Square` to have a single field.

So it seems like what we might actually want here is some way of declaring that when `r::Rectangle{T}` and you write `r.height` and `r.width` you will get something of type `T`. But with overloadable properties, that’s equivalent to saying that `getproperty(r, :height)` and `getproperty(r, :width)` return values of type `T`. What would such a “guarantee” look like in Julia? How do we deal with abstract interfaces in general? We document them and then if someone implements or uses an abstraction wrong they get a runtime error. In other words, the above abstract type declaration would have no effect except acting as documentation that `Rectangle{T}` is _supposed_ to have `width` and `height` properties that return values of type `T`. That just doesn’t seem like a sufficiently compelling feature to add it until it has some more useful meaning.

---

<div class="post-metadata">

**Author:** ![gdkrmr](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdkrmr/32/2791_2.png) [@gdkrmr](https://discourse.julialang.org/u/gdkrmr)\
**Post date:** [January 21, 2019, 5:03pm UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/6 "2019-01-21T17:03:38Z")

</div>

I was trying to enhance `TypeA`, which was provided by some other package without some `AbstractTypeA`:

```julia
module SomeoneElsesPackage
struct TypeA
    a
end

f(x::TypeA) = ...
end

struct TypeB <: TypeA
    a
    b
end

```

Now `f(x::TypeB)` should already be defined and I only need to reimplement some of the functionality.

---

<div class="post-metadata">

**Author:** ![chakravala](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/chakravala/32/6832_2.png) [@chakravala](https://discourse.julialang.org/u/chakravala)\
**Post date:** [January 21, 2019, 5:43pm UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/7 "2019-01-21T17:43:17Z")

</div>

You could make a pull-request on `SomeoneElsesPackage` to create a common abstract type, which would require `SomeoneElsesPackage` methods to dispatch the abstract type instead of the concrete type.

---

<div class="post-metadata">

**Author:** ![Azamat](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/azamat/32/6892_2.png) [@Azamat](https://discourse.julialang.org/u/Azamat)\
**Post date:** [January 21, 2019, 5:55pm UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/8 "2019-01-21T17:55:39Z")

</div>

Composition and method forwarding is the way to go! 🙂

---

<div class="post-metadata">

**Author:** ![gcalderone](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gcalderone/32/1539_2.png) [@gcalderone](https://discourse.julialang.org/u/gcalderone)\
**Post date:** [January 22, 2019, 12:32am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/9 "2019-01-22T00:32:11Z")

</div>

> [@StefanKarpinski](#):
>
> A type can only be instantiated if it is _completely_ specified, and it only makes sense to subtype something if it is _incompletely_ specified. Thus, a type should either be abstract or concrete but not both.

I think there is some tension between the above statement, which is both logical and desirable for performance reasons, and the actual possibility to reuse code.

In practice, it can happens that a type is completely specified for someone, but incompletely specified for someone else. The important word here is _incompletely_: it means that what is available is already a good starting point, but something else is missing.

While this is not a big issue for structure definitions (we can always use macros to copy/paste fields), it is a huge problem for code reuse since:

- abstract types carry no information on the actual data representation;
- methods operate on specific data representations, hence their arguments will be annotated with concrete types;
- but concrete types can not be subtyped, hence those method implementations are locked, and can not be reused.

This problem might be mitigated if we could attach a specific data representation to abstract types. Besides, there are cases where an abstract type will always have one (and only one!!) concrete subtype (consider the `DataFrame` case, thoroughly discussed [here](https://discourse.julialang.org/t/how-to-add-metadata-info-to-a-dataframe/11168): in this case the distinction between `AbstractDataFrame` and `DataFrame` is almost fictitious, and they are actually the same thing).

> [@StefanKarpinski](#):
>
> You end up with attempts to resolve this confusion like the “final” keyword and recommendations against ever subtyping classes that weren’t intended to be abstract. But wouldn’t it be better not to conflate the two things in the first place?

I completely agree that allowing subtyping in all cases brings more damage than advantages, but disallowing it in all cases prevents code reuse (as discussed above). It looks like we need a comporomise in the allowing/disallowing concrete subtyping and abstract/concrete dichotomy…

In [ReusePatterns](https://github.com/gcalderone/ReusePatterns.jl) I explore the possibility to exploit one such compromise through the concept of _quasi-abstract_ type, i.e. a type which:

- can be subtyped like an abstract one;
- can have data representation attached, like a concrete one;
- introduce a performance penalty if used in a container, like an abstract one;
- can be used to annotate method arguments, with no performance penalty, like a concrete one.
- it inherits the structure fields of its ancestors, unlike both abstract and concrete types.
- it is **supposed** to be subtyped, i.e. the author clearly states that it is not `final` and (most importantly) it fosters code reuse.

> [@StefanKarpinski](#):
>
> n other words, the above abstract type declaration would have no effect except acting as documentation that `Rectangle{T}` is _supposed_ to have `width` and `height` properties that return values of type `T` . That just doesn’t seem like a sufficiently compelling feature to add it until it has some more useful meanin

I agree there is no value added in the structure definition, but there is a huge advantage for code reuse: e.g. `function mymethod(input::Rectangle)` could be reused by all `Rectangle` subtypes, since they will all contain the `width` and `height` fields.

In summary: we may safely neglect the problem of concrete subtyping (there are macro for this), but for the purpose of code reuse it might be useful to attach data representation to an abstract type (making it a _not-so-abstract_ one, or _quasi-abstract_). Incidentally, the latter condition brings the possibility of concrete subtyping, even if it was not the original goal.

As R.P. Feynman once said: _sure it can give some practical results, but that’s not why we do it!_. 😉

---

<div class="post-metadata">

**Author:** ![chakravala](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/chakravala/32/6832_2.png) [@chakravala](https://discourse.julialang.org/u/chakravala)\
**Post date:** [January 22, 2019, 12:54am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/10 "2019-01-22T00:54:08Z")

</div>

> [@gcalderone](#):
>
> - abstract types carry no information on the actual data representation;

Abstract types do carry parametric type information, so they can carry some implementation information

```Julia

julia> abstract type AbstractInfo{Data} end

julia> struct SpecificInfo{Data,MoreInfo} <: AbstractInfo{Data} end

```

> [@gcalderone](#):
>
> This problem might be mitigated if we could attach a specific data representation to abstract types.

Have you tried attaching parametric type information to your abstract and concrete types? It can help.

---

<div class="post-metadata">

**Author:** ![Ronis\_BR](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ronis_br/32/50999_2.png) [@Ronis\_BR](https://discourse.julialang.org/u/Ronis_BR)\
**Post date:** [January 22, 2019, 12:56am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/11 "2019-01-22T00:56:05Z")

</div>

I might not been seen it right, but something like this would save me some code.

I have a satellite simulator that I put in a package inside a compiled system image so that other people can use it easily. This simulator let you define the controller and the estimator. Each one has they own abstract type, so that the user can modify the default.

Every time the satellite changes the mode, the controller is different. In some very long simulations that take 2 to 3 hours, it would be bad if something fails because the new controller does not implement all the necessary properties. Hence, I need to programmatically check if everything is right before the beginning of the simulation. If we have such a feature, then the code would not even compile.

Anyway, maybe my approach is wrong and there are better ways to do that, but for my use case now, it will be very nice 🙂

---

<div class="post-metadata">

**Author:** ![Raf](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/raf/32/3383_2.png) [@Raf](https://discourse.julialang.org/u/Raf)\
**Post date:** [January 22, 2019, 1:18am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/12 "2019-01-22T01:18:48Z")

</div>

> [@gcalderone](#):
>
> hence those method implementations are locked

Can’t you just wrap everything in an abstract type and dispatch on that? Then field reuse is taken care of with a macro and the implementation isn’t locked.

I feel the deeper problem (that your package mostly seems to solve) is the point @Ronis_BR makes that when fields are absolutely required in a subtype we are relying on manual checks or error messages for enforcement instead of the compiler. It isn’t very clean, or newb friendly for our package users if they are actively meant to extend things.

---

<div class="post-metadata">

**Author:** ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)\
**Post date:** [January 22, 2019, 6:43am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/13 "2019-01-22T06:43:44Z")

</div>

> [@Ronis\_BR](#):
>
> In some very long simulations that take 2 to 3 hours, it would be bad if something fails because the new controller does not implement all the necessary properties.

There has been some discussion about formalizing interfaces, see eg

> <https://github.com/JuliaLang/julia/issues/6975>
>
> I think this feature request has not yet its own issue although it has been disc…ussed in e.g. #5.
> 
> I think it would be great if we could explicitly define interfaces on abstract types. By interface I mean all methods that have to be implemented to fulfill the abstract type requirements. Currently, the interface is only implicitly defined and it can be scattered over several files so that it is very hard to determine what one has to implement when deriving from an abstract type.
> 
> Interfaces would primary give us two things:
> \- self documentation of interfaces at a single place
> \- better error messages
> 
> Base.graphics has a macro that actually allows to define interfaces by encoding an error message in the fallback implementation. I think this is already very clever. But maybe giving it the following syntax is even neater:
> 
> \`\`\`
> abstract MyType has print, size(::MyType,::Int), push!
> \`\`\`
> 
> Here it would be neat if one could specify different granularities. The \`print\` and \`push!\` declarations only say that there have to be any methods with that name (and \`MyType\` as first parameter) but they don't specify the types. In contrast the \`size\` declaration is completely typed. I think this gives a lot of flexibility and for an untyped interface declaration one could still give quite specific error messages.
> 
> As I have said in #5, such interfaces are basically what is planed in C++ as \`Concept-light\` for C++14 or C++17. And having done quite some C++ template programming I am certain that some formalization in this area would also be good for Julia.

and the issues that reference it (it is a long read).

That said, this may not protect you from runtime errors either. Your best bet is unit testing on a toy problem (small dimensions, or some modification that allows it to run quick).

---

<div class="post-metadata">

**Author:** ![gcalderone](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gcalderone/32/1539_2.png) [@gcalderone](https://discourse.julialang.org/u/gcalderone)\
**Post date:** [January 22, 2019, 9:34am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/14 "2019-01-22T09:34:11Z")

</div>

You can use the concrete subtyping feature in [ReusePattern.jl](https://github.com/gcalderone/ReusePatterns.jl) for this purpose, i.e.:

```julia
@quasiabstract struct Controller
  field1
  field2
  etc.
end

@quasiabstract struct NewController <: Controller
  field3
  etc.
end

function simulate(c::Controller)
  println(c.field1, c.field2)
end

conctroller = NewController(arg1, arg2, arg3)

# The following will surely work (as long as you use `@quasiabstract` to subtype `Controller`)
simulate(controller)
```

---

<div class="post-metadata">

**Author:** ![gcalderone](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gcalderone/32/1539_2.png) [@gcalderone](https://discourse.julialang.org/u/gcalderone)\
**Post date:** [January 22, 2019, 9:42am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/15 "2019-01-22T09:42:04Z")

</div>

> [@Raf](#):
>
> I feel the deeper problem […] is that when fields are absolutely required in a subtype we are relying on manual checks or error messages for enforcement instead of the compiler.

This is just half of the problem.  
The other half is that if package `A` dispatch on concrete type, then package `B` (maintained by another person) has no way to reuse `A`’s functionalities.

Or at best, we should follows @chakravala advice:

> [@chakravala](#):
>
> You could make a pull-request on `SomeoneElsesPackage` to create a common abstract type, which would require `SomeoneElsesPackage` methods to dispatch the abstract type instead of the concrete type.

---

<div class="post-metadata">

**Author:** ![gdkrmr](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdkrmr/32/2791_2.png) [@gdkrmr](https://discourse.julialang.org/u/gdkrmr)\
**Post date:** [January 22, 2019, 10:19am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/16 "2019-01-22T10:19:11Z")

</div>

Thanks for the replies, it must be really tiring for the core devs to listen to the same proposals again and again 🙂. Although I don’t fully understand the problem yet, I see that there are some unresolved issues. It seems like `ReusePatterns.jl` may do what I want.

My intuition wants to simply treat

```julia
struct Rectangle{T<:Real}
    width::T 
    height::T 
end

```

the same way as

```julia
abstract type Rectangle{T<:Real} end

```

is treated now. If you have

```julia
area(x::Rectangle) = x.width * x.height
struct Square{T} <: Rectangle{T}
    width::T 
end  

```

then

```julia
x = Square(3)
area(x)

```

will try to use the method `area(x::Rectangle)` and error because there is no `x.height` unless you specify

```julia
area(x::Square) = x.width * x.width

```

or

```julia
getproperty(x::Square, i)
   # extract width and height
end

```

This would make it really easy to simply add an extra field to a type and to reimplement only the methods that touch the new field without having to use an `AbstractRectangle`.

```julia
struct ColoredRectangle{T<:Real} <: Rectangle{T}
    width::T 
    height::T 
    color::Color 
end

```

Maybe there should be a macro `@make_abstract`:

```julia
@make_abstract Rectangle

```

creates an `AbstractRectangle` type and converts all methods that use `Rectangle` to use `AbstractRectangle`.

---

<div class="post-metadata">

**Author:** ![gcalderone](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gcalderone/32/1539_2.png) [@gcalderone](https://discourse.julialang.org/u/gcalderone)\
**Post date:** [January 22, 2019, 10:41am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/17 "2019-01-22T10:41:46Z")

</div>

> [@gdkrmr](#):
>
> Maybe there should be a macro `@make_abstract` :
> 
> ```julia
> @make_abstract Rectangle
> 
> ```
> 
> creates an `AbstractRectangle` type and converts all methods that use `Rectangle` to use `AbstractRectangle` .

I don’t think this is possible: once you dispatch on concrete type there is no point in defining new methods on abstract types, since the former are more specific.

Also, it is not clear to me if you want `Square` to have the same fields as `Rectangle`. If the answer is yes simply use:

```julia
@quasiabstract struct Rectangle{T<:Real}
    width::T 
    height::T 
end

```

If the answer is no, i.e. if there is not a specific data representation attached to `Rectangle`, then it must be an abstract type:

```julia
abstract type Rectangle{T<:Real} end

```

---

<div class="post-metadata">

**Author:** ![gcalderone](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gcalderone/32/1539_2.png) [@gcalderone](https://discourse.julialang.org/u/gcalderone)\
**Post date:** [January 22, 2019, 10:56am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/18 "2019-01-22T10:56:01Z")

</div>

EDIT: I fixed a bug in `ReusePatterns`.  
The following code:

```julia
@quasiabstract struct Rectangle{T<:Real}
    width::T 
    height::T 
end

```

now correctly produces:

```julia
abstract type Rectangle{T <: Real} <: Any end
struct Concrete_Rectangle{T <: Real} <: Rectangle{T}
    width::T
    height::T
end

(Rectangle{T}(args...; kw...) where T) = Concrete_Rectangle{T <: Real}(args...; kw...)
concretetype(::Type{Rectangle}) = Concrete_Rectangle
concretetype(::Type{Rectangle{T}}) where T = Concrete_Rectangle{T <: Real}

isquasiabstract(::Type{Rectangle}) = true
isquasiabstract(::Type{Rectangle{T}}) where T = true

isquasiconcrete(::Type{Concrete_Rectangle}) = true
isquasiconcrete(::Type{Concrete_Rectangle{T}} where T) = true

```

---

<div class="post-metadata">

**Author:** ![gdkrmr](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdkrmr/32/2791_2.png) [@gdkrmr](https://discourse.julialang.org/u/gdkrmr)\
**Post date:** [January 22, 2019, 11:01am UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/19 "2019-01-22T11:01:04Z")

</div>

> [@gcalderone](#):
>
> > Maybe there should be a macro `@make_abstract` :
> > 
> > ```julia
> > @make_abstract Rectangle
> > 
> > ```
> > 
> > creates an `AbstractRectangle` type and converts all methods that use `Rectangle` to use `AbstractRectangle` .
> 
> I don’t think this is possible: once you dispatch on concrete type there is no point in defining new methods on abstract types, since the former are more specific.

Yes, but I can subtype `AbstractRectangle` and then the methods are defined for the subtypes.

> [@gcalderone](#):
>
> Also, it is not clear to me if you want `Square` to have the same fields as `Rectangle` . If the answer is yes simply use:

I would leave this entirely to the user, if the fields are not defined, then the methods that use those fields simply fail.

---

<div class="post-metadata">

**Author:** ![gcalderone](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gcalderone/32/1539_2.png) [@gcalderone](https://discourse.julialang.org/u/gcalderone)\
**Post date:** [January 22, 2019, 1:44pm UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/20 "2019-01-22T13:44:25Z")

</div>

> [@gdkrmr](#):
>
> Yes, but I can subtype `AbstractRectangle` and then the methods are defined for the subtypes.

OK, but those methods will not be used if there is a more specific method accepting a concrete type.

---

<div class="post-metadata">

**Author:** ![gdkrmr](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gdkrmr/32/2791_2.png) [@gdkrmr](https://discourse.julialang.org/u/gdkrmr)\
**Post date:** [January 22, 2019, 1:59pm UTC](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876/21 "2019-01-22T13:59:48Z")

</div>

```julia
struct Rectangle
    w
    h
end
area(x::Rectangle) = x.h * x.w
width(x::Rectangle) = x.w
@make_abstract Rectangle

struct Square <: AbstractRectangle
    w
end

s = Square(10)
area(s) # fails
width(s) # fine
area(x::Square) = x.w * w.w
area(s) # fine now

```

Yes, you have all the methods implemented two times and the ones for `AbstractRectangle` will not be used, unless they are used by some other subtype (e.g. Square).  
It is not possible to make `Rectangle <: AbstractRectangle`, because you cannot redefine structs.

[Next page](https://discourse.julialang.org/t/why-is-it-impossible-to-subtype-a-struct/19876.md?page=2)
