4
$\begingroup$

Say I have Part of a variable x.

Part[x, 1]

Then, I'll get an error message, as the variable x is not recognised as a list with multiple parts.

If I want to suppress this error, because I know for sure x will have multiple parts, I can use the Quiet function.

Quiet[Part[x, 1], {Part::partd}]

But now imagine that the list variable x itself is an element of another list y such that x=y[[1]].

Quiet[Part[Part[y, 1], 1], {Part::partd}]

I expect this to return y[[1][[1]], however, what I get is y.

Any ideas why this happens? Obviously the examples are simplified working examples, but it should work. How can I get my expected behaviour?

$\endgroup$
4
  • 6
    $\begingroup$ A robust way would be to use Indexed instead of Part. See also here. $\endgroup$ Commented Sep 14, 2018 at 13:36
  • 2
    $\begingroup$ You get y because Part[y, 1] doesn't evaluate if y is atomic. So the outer Part then extracts the first argument of Part[y,1], which is y. This is because Part works on arbitrary expression, not just Lists $\endgroup$ Commented Sep 14, 2018 at 13:45
  • $\begingroup$ @SjoerdSmit Ah, that makes sense. Though adding an Evaluate around the inner Part doesn't seem to work. The Indexed solution is much nicer anyway, as it also doesn't require the Quiet. $\endgroup$
    – LBogaardt
    Commented Sep 14, 2018 at 13:47
  • 1
    $\begingroup$ Evaluate will not do anything here since there's no hold attribute to override (see also mathematica.stackexchange.com/a/180500/43522) . Mathematica tries to evaluate Part[y, 1], but since there's nothing it can evaluate to, it stays the way it is. That's how Mathematica handles most ill-defined expressions: it's part of the symbolic nature of the language. Mathematica uses a term-rewriting style of evaluation and when there's no applicable rules available, things just stay the way they are. $\endgroup$ Commented Sep 14, 2018 at 13:51

1 Answer 1

2
$\begingroup$

Based on Henrik Schumacher's comment (feel free to answer yourself, then you'll get the credits).

A robust way would be to use Indexed instead of Part. See also here.

Example code:

Indexed[x, 1] 
" returns x_1 "
Indexed[Indexed[y, 1], 1]
" returns y_1_1 "
Indexed[Indexed[{{a, b}, {d, c}}, 1], 1]
" returns a "
myFunction[y_, i_, j_]:=Indexed[Indexed[y, i], j]
myFunction[{{a, b}, {d, c}}, 2, 1] 
" returns d "
$\endgroup$

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.