First, a bit of a long introduction to my problem:
I only have a few weeks of Mathematica experience. I am creating a mathematica application that calculates some material properties of steel based on metallurgical functions that include multiple chemical elements. I currently have the chemistry stored in a vector, and the list of elements stored in a second vector of the same length. Here's an example:
elements={"C","Mn","S","P","Si","Cu","Ni","Cr","V","Cb","Mo","Sn","Al","Ca","B","Ti","N","O","Ce","Pb","Bi","W","As","Zn","Sb"};
chemistry={0.032`,1.2`,0.0259`,0.006`,0.04`,0.15`,0.06`,0.04`,0.001`,0.051`,0.167`,0.007`,0.035`,0.0001`,0.`,0.001`,0.0087`,0.0176`,0.0002`,0.0001`,0.`,0.`,0.004`,0.036`,0.`};
I created a function called elem to look up the element name in elements, and find the corresponding entry in chemistry (or any other chemistry list of proper format):
elem[chem_,element_] := chem[[Flatten[Position[elements,element]]]][[1]];
For example, if I want to look up Nickel ("Ni") from the chemistry list, I use the following to get 0.06:
elem[chemistry, "Ni"]
The neat thing about this is when you write a formula using the elem function, the list elements can be used to print the formula in a more user-friendly way for verification. For example, the Titanium to Nitrogen ratio is one of the simpler formulas of interest:
TiByN[chem_] := elem[chem, "Ti"]/elem[chem,"N"]
When called with chemistry, it returns a number (0.114943), but when you call TiByN with elements, it returns the formula Ti/N. This way, I can print a list of formulas in a format that the metallurgists can read when they audit my application.
My question is one of performance. I need to do an optimization involving these formulas, and I think this method of indexing the chemistry is one of my big bottlenecks. Is there any way to precompile a function like elem for the list elements so that the position doesn't have to be looked up for every element in every formula on every iteration of the optimization?
Thanks
TiByN="Ti"/"N"
and then insert numeric values with something likeTiByN /. parameters
whereparameters = Thread[elements->chemistry]
(you could useDispatch
for optimization). With such an approach you can very easily control whether and when to insert values. What you do looks a little like working against the (strong parts of the) system to me... $\endgroup$