How to Convert an Alphanumeric (Reference) Number Containing a Decimal Point to a String in Mathematica

本秂侑毒 提交于 2019-12-04 10:30:28

If you enter DAA76647DAA76647.1 via an input cell in a Mma notebook, Mma will interpret the characters as a multiplication. It even automatically inserts a space between the 7 and the .1 (at least in Mma 8) when you input it.

DAA76647DAA76647 .1 // FullForm

(*Out= Times[0.1`,DAA76647DAA76647] *)

This looks promising:

f[Times[a_, b_]] := ToString[b] <> ToString[a]


EDIT: However, as TomD noted (and I somehow missed), it adds an additional zero to the solution!
f[Times[DAA76647DAA76647 .1]]
(*Out= DAA76647DAA766470.1  *)

%//FullForm
"DAA76647DAA766470.1"

TomD later showed how it is possible to handle this by StringDropping the zero.

This corrected solution will work if only numbers appear to the right of the decimal point and if the left-hand part is not interpreted as a product.

If you try to enter DAA76647.01A Mma will parse it as

(*Out= Times[".01",A,DAA76647]    *)

Notice that it changes the order of the components.

I cannot see a way to handle this reordering.

Alexey Popkov

The call for myfn[DAA76647.1] should be intercepted at the stage of converting Input to an expression.

You can see that Input has the form RowBox[{"myfn", "[", RowBox[{"DAA76647", ".1"}], "]"}]:

In[1]:= myfn[DAA76647 .1]
DownValues[InString]

Out[1]= myfn[0.1 DAA76647]

Out[2]= {HoldPattern[InString[1]] :> 
  ToString[RowBox[{"myfn", "[", RowBox[{"DAA76647", ".1"}], "]"}], 
   InputForm], 
 HoldPattern[InString[2]] :> 
  ToString[RowBox[{"DownValues", "[", "InString", "]"}], InputForm]}

We could create a special case definition for MakeExpression:

MakeExpression[RowBox[{"myfn", "[", RowBox[{"DAA76647", ".1"}], "]"}],
   f_] := MakeExpression[RowBox[{"myfn", "[", "\"DAA76647.1\"", "]"}],
   f]

You can see that now myfn[DAA76647 .1] works as desired:

In[4]:= myfn[DAA76647 .1]//FullForm
Out[4]//FullForm= myfn["DAA76647.1"]

This approach can be generalized to something like

MakeExpression[RowBox[{"myfn", "[", expr:Except[_String], "]"}], form_] := 
 With[{mexpr = StringJoin[expr /. RowBox -> List]}, Hold[myfn[mexpr]]]
myfn[expr_String] := (* what ever you want to do here *)

Note that the Except[_String] part is not really needed... since the following code won't do anything wrong with a String.
At the moment, the code only works with simple examples with one-dimensional box structure. If you want something that handles more general input, you might want to add error checking or extra rules for things like SuperscriptBox and friends. Or hit it with the hammer of Evaluate[Alternatives @@ Symbol /@ Names["*Box"]] -> List to make all Box objects become lists and flatten everything down.

I don't think you can directly type this between the brackets of a function call, but would

myfn[InputString[]] 

work for you?

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!