4
$\begingroup$

I am trying to create a table with conditionals inline. For example, I'd like to create a 2 dimensional table like this:

Table[{i, j} -> 1, {i, 1, 3}, {j, 1, 3}]

Now, I'd like Table to generate values only if i != 1. It should be easy, but I'm lost. I've tried several approaches, like the following, but I don't get what I want in a neat way:

Table[If[i != 1, {i, j} -> 1], {i, 1, 3}, {j, 1, 3}]

{{Null, Null, Null}, {{2, 1} -> 1, {2, 2} -> 1, {2, 3} -> 1}, {{3, 1} -> 1, {3, 2} -> 1, {3, 3} -> 1}}

I know, I could delete cases, but there must be a clean and simple way!

$\endgroup$
7
  • 2
    $\begingroup$ If[..., bla, Unevalauted@Sequence[]] $\endgroup$
    – Rojo
    Commented May 3, 2013 at 11:10
  • $\begingroup$ Seems to be a dupe of this. $\endgroup$ Commented May 3, 2013 at 11:10
  • $\begingroup$ @J.M. I actually want to use just Table, so no loops (it is too easy with a loop!) or other commands. Moreover, I'd like (as in the title) to use an inline conditional. $\endgroup$
    – senseiwa
    Commented May 3, 2013 at 11:20
  • 4
    $\begingroup$ I like this one: Most@ArrayRules@SparseArray[{i_, j_} /; i != 1 -> 1, {3, 3}] $\endgroup$ Commented May 3, 2013 at 12:10
  • 1
    $\begingroup$ I would suggest using Sow and Reap: Reap[Do[If[i != 1, Sow[{i, j} -> 1]], {i, 3}, {j, 3}]][[-1, 1]] $\endgroup$ Commented May 3, 2013 at 12:15

1 Answer 1

3
$\begingroup$

To my mind, it would be better to control the values i is allowed take in the second argument to Table rather than in the first. For your particular example that means writing the very simple and efficient

Table[{i, j} -> 1, {i, 2, 3}, {j, 1, 3}]

{{{2, 1} -> 1, {2, 2} -> 1, {2, 3} -> 1},
{{3, 1} -> 1, {3, 2} -> 1, {3, 3} -> 1}}

This approach can be quit general. For example

Table[{i, j} -> 1, {i, #^2 & /@ Range[5]}, {j, 1, 3}]

{{{1, 1} -> 1, {1, 2} -> 1, {1, 3} -> 1},
{{4, 1} -> 1, {4, 2} -> 1, {4, 3} -> 1},
{{9, 1} -> 1, {9, 2} -> 1, {9, 3} -> 1},
{{16, 1} -> 1, {16, 2} -> 1, {16, 3} -> 1},
{{25, 1} -> 1}, {25, 2} -> 1, {25, 3} -> 1}}

Edit

Adding this to cover the case raised in senseiwa's comment:

I am not sure how I can use your solution for, say, i != K, given a K > 0.

There are many possibilities. Here is one.

With[{k = 4}, Table[{i, j} -> 1, {i, Delete[Range[5], k]}, {j, 1, 3}]]

{{{1, 1} -> 1, {1, 2} -> 1, {1, 3} -> 1},
{{2, 1} -> 1, {2, 2} -> 1, {2, 3} -> 1},
{{3, 1} -> 1, {3, 2} -> 1, {3, 3} -> 1},
{{5, 1} -> 1, {5, 2} -> 1, {5, 3} -> 1}}

Perhaps I should remark that the index specifier for i (or any index) in a Table expression can be a list specifying the exactly those indexes that i should obtain. By creating such a list, either within the Table expression (as I have done here) or external to it, it possible to select any subset of an index range.

$\endgroup$
1
  • $\begingroup$ I am not sure how I can use your solution for, say, i != K, given a K > 0... $\endgroup$
    – senseiwa
    Commented May 8, 2013 at 7:56

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

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