# Argument order in \`kron(A,B)\`

**URL:** https://discourse.julialang.org/t/argument-order-in-kron-a-b/47481
**Category:** General Usage
**Created:** [September 29, 2020, 12:36pm UTC](https://discourse.julialang.org/t/argument-order-in-kron-a-b/47481 "2020-09-29T12:36:40Z")
**Posts on this page:** 6
**Page:** 1

<div class="post-metadata">

### Author: ![ettersi](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ettersi/32/6829_2.png) [@ettersi](https://discourse.julialang.org/u/ettersi)
#### Post date: [September 29, 2020, 12:36pm UTC](https://discourse.julialang.org/t/argument-order-in-kron-a-b/47481/1 "2020-09-29T12:36:40Z")

</div>

Julia defines `kron(A,B)` such that

```julia
kron(A,B)*vec(C) = vec(B*C*A')

```

while if I were to have my way I would define `kron(A,B)` such that

```julia
kron(A,B)*vec(C) = vec(A*C*B') # A and B are swapped

```

Given Julia’s history of [taking things seriously](https://discourse.julialang.org/t/please-dont-use-taking-seriously-as-a-topic-name), I am sure there are good reasons for why `kron` is the way it is, but I don’t see them. Can someone help me?

---

<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: [September 29, 2020, 12:47pm UTC](https://discourse.julialang.org/t/argument-order-in-kron-a-b/47481/2 "2020-09-29T12:47:06Z")

</div>

> [@ettersi](#):
>
> Julia defines `kron(A,B)` such that

This[¹](https://en.wikipedia.org/wiki/Kronecker_product) definition[²](https://mathworld.wolfram.com/KroneckerProduct.html) considerably[³](https://encyclopediaofmath.org/index.php?title=Tensor_product) predates[⁴](https://www.mathworks.com/help/matlab/ref/kron.html) Julia,[⁵](https://numpy.org/doc/stable/reference/generated/numpy.kron.html) for better or for worse.

---

<div class="post-metadata">

### Author: ![ettersi](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ettersi/32/6829_2.png) [@ettersi](https://discourse.julialang.org/u/ettersi)
#### Post date: [September 29, 2020, 12:55pm UTC](https://discourse.julialang.org/t/argument-order-in-kron-a-b/47481/3 "2020-09-29T12:55:07Z")

</div>

Thank you very much for the speedy and well researched answer! Interesting that all languages agree on this while they can’t even agree on whether matrices should be stored in row- or column-major order…

---

<div class="post-metadata">

### Author: ![ericphanson](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ericphanson/32/215186_2.png) [@ericphanson](https://discourse.julialang.org/u/ericphanson)
#### Post date: [September 29, 2020, 1:08pm UTC](https://discourse.julialang.org/t/argument-order-in-kron-a-b/47481/4 "2020-09-29T13:08:43Z")

</div>

There was a PR to add a `tensor` function that would have the column-major compatible order (as well as generalize to higher dimensional arrays), [https://github.com/JuliaLang/julia/pull/35150](https://github.com/JuliaLang/julia/pull/35150), but it was reverted in [https://github.com/JuliaLang/julia/pull/35744](https://github.com/JuliaLang/julia/pull/35744), so check those out for some more discussion on the Julia side. This functionality is now in a package: [https://github.com/JuliaMath/TensorCore.jl](https://github.com/JuliaMath/TensorCore.jl).

FWIW I think it’s unfortunate that we have `kron` in Base, but no function with the “correct” order with as much visibility, since I think it can be very confusing for newcomers as to why textbook identities like `A*B ≈ reshape((kron(A, I(d)))*vec(B), d, d)` don’t work in Julia, but do in row-major languages. But I think the solution now is to promote packages like TensorCore.

---

<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: [September 29, 2020, 1:51pm UTC](https://discourse.julialang.org/t/argument-order-in-kron-a-b/47481/5 "2020-09-29T13:51:28Z")

</div>

> [@ericphanson](#):
>
> unfortunate that we have `kron` in Base, but no function with the “correct” order

Given that pretty much everyone uses this order, it is somewhat difficult to argue that it isn’t the “correct” one for [least astonishment](https://en.wikipedia.org/wiki/Principle_of_least_astonishment). If the order was reversed, a lot of users could complain, and reasonably so.

While some orders are more convenient for some applications, arguing about the “correct” one is usually a pointless exercise because the criterion is very subjective. As long as the choice is reasonable and it is documented, it should be fine.

---

<div class="post-metadata">

### Author: ![ericphanson](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ericphanson/32/215186_2.png) [@ericphanson](https://discourse.julialang.org/u/ericphanson)
#### Post date: [September 29, 2020, 1:59pm UTC](https://discourse.julialang.org/t/argument-order-in-kron-a-b/47481/6 "2020-09-29T13:59:07Z")

</div>

Alright, I probably shouldn’t have used the word “correct” here. I can agree that the name `kron` means a certain order and it’s the one implemented in Base

What I meant to say is that often one arrives at `kron` thinking to use it as a tensor product, and for that use-case the order does not interoperate well with column-major operations like `vec` and `reshape`, and is in some way “incorrect” for that usage (although not incorrect for a function named `kron`). So I think it would be helpful if the alternative was more visible, so that people with this use case can find it (people who perhaps aren’t already aware of the difference between `kron` and a tensor product).
