Group Abstract Group Abstract

Message Boards Message Boards

0
|
7.7K Views
|
16 Replies
|
11 Total Likes
View groups...
Share
Share this post:

Test for the position of the first non-numeric value?

Posted 9 years ago

Hello

I have the feeling that my question is pretty basic, but the answer will help me to understand a bit more on the Wolfram Language. Here it is:

Consider the following list:

{0, -1 + x^2 y^2, -x^3 + 2 x^2 y + x^5 y^2}

How can I find the position of the first element of the list that is not numeric? I have tried to use Position with pattern _?NumericQ[#] & (just to see if it finds 1) but it didn't work. This shows that I don't know how this type of expressions works

The solution does not need to use Position. I've just used for the sake of understanding expressions. Different solutions are welcome.

Thank you for your time and patience.

Ed

POSTED BY: Eduardo Mendes
16 Replies

I just send it to them, if I hear some details I will share it here (if possible as this info might be subject to an NDA)...

POSTED BY: Sander Huisman
Posted 9 years ago

Thank you all ever so much.

POSTED BY: Eduardo Mendes

Perfect!

It is very interesting to know what is the cause of this situation...

Especially compared to SelectFirst, as these are (nearly) the same functions... One keeps a counter, the other gives the item, should be nearly same timings.... My results are from an upcoming version, so if it is a 'bug' it is not yet fixed in the next release. I will send this info to Wolfram...

POSTED BY: Sander Huisman

It seems very strange such a big time difference for the function LengthWhile.

Very surprising that LengthWhile is so slow, perhaps because it is not compiled? while any pattern-matching is (either directly or JIT). If you know that is in 'ordinary' number then you can speed it up even more. Function-testing is much slower than checking the Head of an expression. Also NumberQ instead of NumericQ can be a bit faster. It all depends on what you consider a number... (btw you could also add |_Complex if you like...

tList=RandomChoice[{a,b,c},1000000];
tList[[777777]]=1;

Position[NumericQ/@tList,True][[1]]//AbsoluteTiming
Position[tList,_?NumericQ,1]//AbsoluteTiming
Position[tList,_?(NumericQ[#]&),1]//AbsoluteTiming
FirstPosition[tList,_?NumericQ,1]//AbsoluteTiming
FirstCase[tList,_?NumericQ]//AbsoluteTiming
SelectFirst[tList,NumericQ]//AbsoluteTiming
(LengthWhile[tList,Not@*NumericQ]+1)//AbsoluteTiming

BarChart@{Position[NumericQ/@tList,True][[1]]//AbsoluteTiming,Position[tList,_?NumericQ,1]//AbsoluteTiming,Position[tList,_?(NumericQ[#]&),1]//AbsoluteTiming,FirstPosition[tList,_?NumericQ,1]//AbsoluteTiming,FirstCase[tList,_?NumericQ]//AbsoluteTiming,
SelectFirst[tList,NumericQ]//AbsoluteTiming,
SelectFirst[tList,NumberQ]//AbsoluteTiming,(LengthWhile[tList,Not@*NumericQ]+1)//AbsoluteTiming,
FirstPosition[tList,_Real|_Integer,1]//AbsoluteTiming,
FirstCase[tList,_Real|_Integer]//AbsoluteTiming
}[[All,1]]

enter image description here

POSTED BY: Sander Huisman

It is the worst choice!

In[1]:= tList = RandomChoice[{"a", "b", "c"}, 1000000];
tList[[777777]] = 1;

In[3]:= Position[NumericQ /@ tList, True][[1]] // AbsoluteTiming
Position[tList, _?NumericQ, 1] // AbsoluteTiming
Position[tList, _?(NumericQ[#] &), 1] // AbsoluteTiming
FirstPosition[tList, _?NumericQ, 1] // AbsoluteTiming
FirstCase[tList, _?NumericQ] // AbsoluteTiming
SelectFirst[tList, NumericQ] // AbsoluteTiming
(LengthWhile[tList, Not@*NumericQ] + 1) // AbsoluteTiming

Out[3]= {0.369993, {777777}}

Out[4]= {0.39994, {{777777}}}

Out[5]= {0.820059, {{777777}}}

Out[6]= {0.32599, {777777}}

Out[7]= {0.302233, 1}

Out[8]= {0.211421, 1}

Out[9]= {2.50185, 777777}

In[10]:= BarChart@{
   Position[NumericQ /@ tList, True][[1]] // AbsoluteTiming,
   Position[tList, _?NumericQ, 1] // AbsoluteTiming,
   Position[tList, _?(NumericQ[#] &), 1] // AbsoluteTiming,
   FirstPosition[tList, _?NumericQ, 1] // AbsoluteTiming,
   FirstCase[tList, _?NumericQ] // AbsoluteTiming,
   SelectFirst[tList, NumericQ] // AbsoluteTiming,
   (LengthWhile[tList, Not@*NumericQ] + 1) // AbsoluteTiming
   }[[All, 1]]

enter image description here

POSTED BY: Sander Huisman
Posted 9 years ago
POSTED BY: Bill Simpson
Posted 9 years ago

Many thanks. LengthWhile is definitely a good alternative.

POSTED BY: Eduardo Mendes
POSTED BY: Sander Huisman

Absolutely well explained by Bill. Only for the simplicity it may be observed additionally that

In[1]:= Position[{0, -1 + x^2 y^2, -x^3 + 2 x^2 y + x^5 y^2}, _?NumericQ, 1]

Out[1]= {{1}}

In[2]:= Position[{0, -1 + x^2 y^2, -x^3 + 2 x^2 y + x^5 y^2}, _?(NumericQ[#] &), 1]

Out[2]= {{1}}

In[3]:= FirstPosition[{0, -1 + x^2 y^2, -x^3 + 2 x^2 y + x^5 y^2}, _?NumericQ, 1]

Out[3]= {1}
Posted 9 years ago

Dear Bill

Thank you ever so much. I will definitely explore your examples further

Regards

Ed

POSTED BY: Eduardo Mendes
Posted 9 years ago

Many thanks.

Would you mind tell me why _?NumericQ[#] & won't work?

Position[{0, -1 + x^2 y^2, -x^3 + 2 x^2 y + 
   x^5 y^2}, _?NumericQ[#]  &]
POSTED BY: Eduardo Mendes
In[1]:= Position[NumericQ /@ {0, -1 + x^2 y^2, -x^3 + 2 x^2 y + x^5 y^2}, True][[1]]

Out[1]= {1}
Reply to this discussion
Community posts can be styled and formatted using the Markdown syntax.
Reply Preview
Attachments
Remove
or Discard