This question already has an answer here:

Here's a simple example. Suppose we want to find the off-diagonal matrix of m:


This can be solved fairly simply by extracting a list of the diagonal elements, re-creating the diagonal matrix from these, and removing them from the full matrix to get the off-diagonal elements:

m - DiagonalMatrix[Diagonal[m]]  

to get


Now, this was a fairly simple solution to the given problem, but what I'm wondering is if there is a way to write something akin to

(Identity - DiagonalMatrix@Diagonal)[m]  

To get the same result. In this simple example, not much would be gained by doing this, but I just thought it could be interesting in more complicated problems and help make the code resemble more closely the underlying mathematics in some cases.


marked as duplicate by Mr.Wizard Jun 21 '15 at 10:27

This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.

  • 1
    $\begingroup$ # - DiagonalMatrix[Diagonal[#]] &[m] ? Of course you can add Identity[#] at the beginning. $\endgroup$ – Kuba Feb 18 '14 at 20:39
  • 4
    $\begingroup$ Also look at Composition for chaining long functions. It will greatly improve the clarity of your code. $\endgroup$ – rm -rf Feb 18 '14 at 20:45
  • 6
    $\begingroup$ You should look at Through too, e.g. Through[(f + g + h)[x]] gives f[x] + g[x] + h[x]. $\endgroup$ – Simon Woods Feb 18 '14 at 21:32
  • 1
    $\begingroup$ @Steve It doesn't work for two reasons: @ doesn't denote function composition, but function application (use Composition for function composition) and because Through only goes in one level while here we actually have an expression of the form (a + (-1)*b), not of a simpler form a-b. I'm afraid there's no easy and simple solution to your problem other than building pure functions as in (Identity[#] - DiagonalMatrix@Diagonal[#]) &[m]. $\endgroup$ – Szabolcs Feb 18 '14 at 22:42
  • 2
    $\begingroup$ Following Rojo's idea, you can do operatorApply[f_[x__]] := Replace[f, s_Symbol :> s[x], {0, Infinity}, Heads -> False]. See where this goes wrong: operatorApply[(Sin + 1)[x]] transforms to Sin[x]+1, all is fine. Now what about operatorApply[(Sin + Pi)[x]]? You get Pi[x] + Sin[x], wrong! This is probably why it's not a built-in function. I don't see a good way around this problem, i.e. it's not a problem with my implementation but an inherent problem to the idea: it's not possible to distinguish functions from other symbols, e.g. constants. $\endgroup$ – Szabolcs Feb 18 '14 at 23:35

In version 10 we can use the new shorthand notation for Composition to write

Through@(Identity + Minus@*DiagonalMatrix@*Diagonal)[m]

(* {{0, 2}, {3, 0}} *)

As noted in the comments, Through@(a - b)[x] won't work the way we'd like because a - b is represented internally as a + (-1)*b. Composing with Minus gets around this problem.


Not the answer you're looking for? Browse other questions tagged or ask your own question.