Re: Unexpected behavior with Thread
- To: mathgroup at smc.vnet.net
- Subject: [mg21103] Re: [mg21073] Unexpected behavior with Thread
- From: Hartmut Wolf <hwolf at debis.com>
- Date: Fri, 17 Dec 1999 01:21:03 -0500 (EST)
- Organization: debis Systemhaus
- References: <199912130451.XAA16292@smc.vnet.net>
- Sender: owner-wri-mathgroup at wolfram.com
Joel Cannon schrieb: > > I have encountered an unexpected behavior when using Thread. I have a > function getTorque that I am trying to Thread over two lists. When I > Thread getTorque over the lists, it does not work. However, If I > thread a function "f" over the same lists, and then make the > transformation f->getTorque, it works as it should. Here is what it > looks like. Apologies for the output with all the formatting > commands. I have not been able to get rid of it. The functions and > lists are at the bottom of this post. > > ********************************************* > Here is what happens when I Thread the function getTorque. > > In[95]:= getTorque[rwheels, fwheels, 0] // Thread > > Dot::"dotsh": "Tensors \!\({\(\({1, 0, 0}\)\), \(\({0, 1, 0}\)\), \(\({0, 0, \ > 1}\)\)}\) and \!\({\(\({\(\(\(\(-mu\)\)\\ n1\)\), 0, n1}\)\), \ > \(\({\(\(\(\(-mu\)\)\\ n2\)\), 0, n2}\)\)}\) have incompatible shapes." > > Out[95]= > \!\({CrossProduct[{w\/2, > 0, \(-zcm\)}, {{1, 0, 0}, {0, 1, 0}, {0, 0, 1}} . {{\(-mu\)\ n1, 0, > n1}, {\(-mu\)\ n2, 0, n2}}], > CrossProduct[{\(-\(w\/2\)\), > 0, \(-zcm\)}, {{1, 0, 0}, {0, 1, 0}, {0, 0, 1}} . {{\(-mu\)\ n1, 0, > n1}, {\(-mu\)\ n2, 0, n2}}]}\) > > ************************************************** > Here I thread the undefined function "f" and /. f->getTorque > > In[110]:= > (f[rwheels, fwheels, 0] // Thread) /. f -> getTorque > > Out[110]= > \!\({{0, \(-\(\(n1\ w\)\/2\)\) + mu\ n1\ zcm, > 0}, {0, \(n2\ w\)\/2 + mu\ n2\ zcm, 0}}\)° > > ***************************************************************** > For reference, here are the functions and the lists that I am > threading over. > > getTorque[rbody_, fspace_, psi_] := CrossProduct[rbody, roty[-psi] . fspace] > > roty[t_] := {{Cos[t], 0, Sin[t]}, {0, 1, 0}, {-Sin[t], 0, Cos[t]}} > > rwheels = {{w/2, 0, -zcm}, {-w/2, 0, -zcm}} > > fwheels = {{-(mu*n1), 0, n1}, {-(mu*n2), 0, n2}} > **************************************************** > > Thanks to anyone who can help. > > ------------------------------------------------------------------------------ > Joel W. Cannon | (724)223-6146 > Physics Department | > Washington and Jefferson College | > Washington, PA 15301 | > > Dear Joel, you do have a solution, namely your In[110] above, howerver a little bit more convenient is: In[64]:= Thread[Hold[getTorque][rwheels, fwheels, 0]] // ReleaseHold Out[64]= {CrossProduct[{w/2, 0, -zcm}, {-mu n1, 0, n1}], CrossProduct[{-w/2, 0, -zcm}, {-mu n2, 0, n2}]} (which is essentially the same, except that you dispense with the undefined symbol f). Also MapThread will do: In[75]:= MapThread[getTorque2, {rwheels, fwheels, {0, 0}}] Out[75]= {CrossProduct[{w/2, 0, -zcm}, {-mu n1, 0, n1}], CrossProduct[{-w/2, 0, -zcm}, {-mu n2, 0, n2}]} but perhaps you'll dislike the list which you now must substitute for your phi argument. To understand what Thread does in your case, observe In[76]:= Attributes[Thread] Out[76]= {Protected} So Thread evaluates it's arguments (and it need's to do so, else it couldn't work). So your In[95] above is equivalent with CrossProduct[rwheels, roty[-psi].fwheels] // Thread and now it becomes clear what happens. The thread-list comes across with Dot, which will evaluate before threading over fwheels is done. It will run into the error and then threading is done over rwheels (only). You can avoid this if you take a different head for threading: In[144]:= ClearAll[getTorque] In[145]:= getTorque[rbody_, fspace_, psi_] := CrossProduct[rbody, Thread[roty[-psi].fspace, h]] In[146]:= Thread[getTorque[h @@ rwheels, h @@ fwheels, 0], h] Out[146]= h[CrossProduct[{w/2, 0, -zcm}, {-mu n1, 0, n1}], CrossProduct[{-w/2, 0, -zcm}, {-mu n2, 0, n2}]] h is nothing but a container for threading (which Dot can't misconstrue). And getTorque still works for scalar arguments: In[147]:= getTorque[rwheels[[1]], fwheels[[1]], 0] Out[147]= CrossProduct[{w2, 0, -zcm}, {-mu n1, 0, n1}] My recommendation however is to use Thread with Hold, ReleaseHold! Kind regards, Hartmut
- References:
- Unexpected behavior with Thread
- From: Joel Cannon <jcannon@jcannon.washjeff.edu>
- Unexpected behavior with Thread