{"id":45,"date":"2009-02-04T22:19:21","date_gmt":"2009-02-04T22:19:21","guid":{"rendered":"https:\/\/blogs.mathworks.com\/seth\/2009\/02\/04\/how-do-i-test-for-nan-in-my-model\/"},"modified":"2009-02-04T22:19:21","modified_gmt":"2009-02-04T22:19:21","slug":"how-do-i-test-for-nan-in-my-model","status":"publish","type":"post","link":"https:\/\/blogs.mathworks.com\/simulink\/2009\/02\/04\/how-do-i-test-for-nan-in-my-model\/","title":{"rendered":"How do I test for NaN in my model?"},"content":{"rendered":"\r\n<p>This week I want to pose a brainteaser that my colleague\r\nJeff had to solve this week.\u00a0 Imagine you need to detect the condition where a\r\nsignal value might become NaN (<strong>N<\/strong>ot <strong>A<\/strong> <strong>N<\/strong>umber).\u00a0 How do you\r\ntest for that in Simulink?<\/p>\r\n\r\n<p><strong>What is a NaN?<\/strong><\/p>\r\n\r\n<p><a href=\"http:\/\/en.wikipedia.org\/wiki\/NaN\">NaN means <strong>N<\/strong>ot-<strong>A<\/strong>-<strong>N<\/strong>umber<\/a>.\u00a0\r\nIn general math terms, this is the result for special cases, which are undefined.\u00a0\r\nIn general computing terms, operations return NaN for invalid inputs.\u00a0 For\r\nexample:<\/p>\r\n\r\n<p style='margin-bottom:0in;margin-bottom:.0001pt;line-height:\r\nnormal;text-autospace:none'><span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>&gt;&gt; Inf*0<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>ans =<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>\u00a0\u00a0 NaN<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>&gt;&gt; 0\/0<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>ans =<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>\u00a0\u00a0 NaN<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>&gt;&gt; Inf\/Inf<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>ans =<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>\u00a0\u00a0 NaN<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>&gt;&gt; Inf-Inf<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>ans =<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>\u00a0\u00a0 NaN<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\"'>&nbsp;<\/span><\/p>\r\n\r\n<p>If you are writing code and need to protect against invalid\r\ninputs, detecting this could be important.<\/p>\r\n\r\n<p><strong>ISNAN?<\/strong><\/p>\r\n\r\n<p>In MATLAB we have the function <a\r\nhref=\"https:\/\/www.mathworks.com\/help\/releases\/R2008b\/techdoc\/ref\/isnan.html\">ISNAN<\/a>.\u00a0\r\nISNAN is a MATLAB function, which we could call from Simulink.<\/p>\r\n\r\n<p style='margin-bottom:0in;margin-bottom:.0001pt;line-height:\r\nnormal;text-autospace:none'><span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>&gt;&gt; x = 0\/0<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>x =<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>\u00a0\u00a0 NaN<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>&gt;&gt; isnan(x)<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>ans =<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>\u00a0\u00a0\u00a0\u00a0 1<\/span><\/p>\r\n\r\n\r\n\r\n<p>In some ways, that feels like cheating.\u00a0 If we were\r\ndeveloping this algorithm to run on an embedded system, MATLAB will not be\r\navailable.<\/p>\r\n\r\n<p><strong>First try, Diagnostics<\/strong><\/p>\r\n\r\n<p>The first idea I had was to look at the diagnostics.\u00a0 I\r\nremembered seeing a warning about NaNs once during a simulation, so there might\r\nbe a way to turn on a diagnostic to detect this.<\/p>\r\n\r\n<p><img decoding=\"async\" src=\"https:\/\/blogs.mathworks.com\/images\/seth\/2009Q1\/NaN_diagnostic.png\" alt=\"Simulink configuration parameters\"><\/p>\r\n\r\n<p>We found the diagnostic in the Data Validity page of the\r\nConfiguration Parameters.\u00a0 This diagnostic will check for Inf or NaN signals in\r\na block output, but that doesn\u2019t help if we want the model to do something\r\nreactive with that information.\u00a0 This diagnostic is purely informative.<\/p>\r\n\r\n<p><strong>NaN has a specific bit pattern<\/strong><\/p>\r\n\r\n<p>What about testing the bit pattern?\u00a0 Using MATLAB I can see\r\nwhat that pattern is in HEX:<\/p>\r\n\r\n<p style='margin-bottom:0in;margin-bottom:.0001pt;line-height:\r\nnormal;text-autospace:none'><span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>&gt;&gt; format <\/span><span style='font-size:12.0pt;font-family:\r\n\"Courier New\";color:#A020F0'>hex<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>&gt;&gt; NaN<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>ans =<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>\u00a0\u00a0 fff8000000000000<\/span><\/p>\r\n\r\n\r\n<p>We did try the bit operations, but ran into some\r\ndifficulties.\u00a0 NaN is a floating-point number, and all the bit processing\r\nblocks are built for working with integers.\u00a0 In this case, working with a floating-point\r\nnumber would require some contortions to get the bit pattern.\u00a0 Once we had it,\r\nwe could use the other Bitwise Operator block to test for the pattern we were\r\nlooking for, but we didn\u2019t get that working before we had another realization.<\/p>\r\n\r\n<p><strong>Comparison with NaN is different from all other numbers<\/strong><\/p>\r\n\r\n<p>That was the \u201cEureka!\u201d moment: NaN has special properties!\u00a0 Math\r\noperations performed with NaN result in a NaN\u00a0 (x+NaN = NaN).\u00a0 Comparisons to a\r\nNaN return false.\u00a0 For example:<\/p>\r\n\r\n<p style='margin-bottom:0in;margin-bottom:.0001pt;line-height:\r\nnormal;text-autospace:none'><span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>&gt;&gt; NaN&lt;1<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>ans =<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>\u00a0\u00a0\u00a0\u00a0 0<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>&gt;&gt; NaN&lt;=Inf<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>ans =<\/span><br>\r\n\r\n\r\n<span style='font-size:12.0pt;font-family:\"Courier New\";\r\ncolor:black'>\u00a0\u00a0\u00a0\u00a0 0<\/span><\/p>\r\n\r\n\r\n\r\n<p>Comparison with Inf is pretty interesting because we couldn\u2019t\r\nthink of any other numbers that would return FALSE for <span style='font-family:\r\n\"Courier New\"'>X&lt;=Inf<\/span>, except NaN.\u00a0 Even if <span style='font-family:\r\n\"Courier New\"'>X=Inf<\/span>, this should return TRUE.\u00a0 In Simulink, the test\r\nmodel looked like this:<\/p>\r\n\r\n<p><img decoding=\"async\" src=\"https:\/\/blogs.mathworks.com\/images\/seth\/2009Q1\/NaNlessThanInf.png\" alt=\"ISNAN built with Simulink blocks using a Compare to Constant block and Logical Operator\"><\/p>\r\n\r\n<p>Using the logical operation, NOT, we can pass any signal\r\nthrough these blocks and make our own ISNAN block.\u00a0 Another interesting\r\nproperty of NaN is that it is the ONLY number not equal to itself.\u00a0 An\r\nalternative model, arguably more streamlined, uses just the Relational Operator\r\nto test the NOT Equals condition and compares the signal to itself.<\/p>\r\n\r\n<p><img decoding=\"async\" src=\"https:\/\/blogs.mathworks.com\/images\/seth\/2009Q1\/NaNnotEqualNaN.png\" alt=\"ISNAN built with Simulink blocks using the Relational Operator\"><\/p>\r\n\r\n<p>All numbers EXCEPT NaN should return FALSE for this test.\u00a0\r\nWe double-checked it by sending infinity through the same construct.<\/p>\r\n\r\n<p><strong>The Final Answer?<\/strong><\/p>\r\n\r\n<p>Have you done any interesting mathematical operations to\r\ndeal with special floating-point numbers?\u00a0 Can you think of another way to do\r\nthis?\u00a0 Did you ever have to deal with quiet NaNs versus signaling NaNs?\u00a0 Tell\r\nme about it with a <a href=\"https:\/\/blogs.mathworks.com\/seth\/?p=45&amp;#comment\">comment\r\nhere<\/a>.<\/p>\r\n","protected":false},"excerpt":{"rendered":"<p>\r\nThis week I want to pose a brainteaser that my colleague\r\nJeff had to solve this week.\u00a0 Imagine you need to detect the condition where a\r\nsignal value might become NaN (Not A Number).\u00a0 How do... <a class=\"read-more\" href=\"https:\/\/blogs.mathworks.com\/simulink\/2009\/02\/04\/how-do-i-test-for-nan-in-my-model\/\">read more >><\/a><\/p>","protected":false},"author":40,"featured_media":0,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":[],"categories":[67,76],"tags":[77,441],"_links":{"self":[{"href":"https:\/\/blogs.mathworks.com\/simulink\/wp-json\/wp\/v2\/posts\/45"}],"collection":[{"href":"https:\/\/blogs.mathworks.com\/simulink\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blogs.mathworks.com\/simulink\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blogs.mathworks.com\/simulink\/wp-json\/wp\/v2\/users\/40"}],"replies":[{"embeddable":true,"href":"https:\/\/blogs.mathworks.com\/simulink\/wp-json\/wp\/v2\/comments?post=45"}],"version-history":[{"count":0,"href":"https:\/\/blogs.mathworks.com\/simulink\/wp-json\/wp\/v2\/posts\/45\/revisions"}],"wp:attachment":[{"href":"https:\/\/blogs.mathworks.com\/simulink\/wp-json\/wp\/v2\/media?parent=45"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blogs.mathworks.com\/simulink\/wp-json\/wp\/v2\/categories?post=45"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blogs.mathworks.com\/simulink\/wp-json\/wp\/v2\/tags?post=45"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}