TeX - LaTeX Asked by alex dinovitser on September 28, 2021
I am trying to use datatools DTLfetch
to grab a real number from a database loaded from a .csv file, and then pass this numeric argument to FPeval
.
Problem is that DTLfetch
always seems to return a string instead of a numeric, which gives an error because FP can’t handle string datatypes.
DTLgetvalue
always returns the desired numeric datatype and everything works, however, I really need DTLfetch
.
I have spent the last two days trying to figure out how to convert a string to a numeric datatype in LaTeX, or alternatively, how to get DTLfetch
to return a numeric value instead of a string.
Is LaTeX seriously deficient in this capability? or am I missing something fundamental? Should I use Sagetex to do the conversion?
Many thanks!
TeX is a macro language, it does not have any other types than strings. (There are typed registers, but they are not relevant here)
The problem is not that DTLfetch
"returns" a string, it is that DTLfetch
is not expandable.
Non-expandable macros like DTLfetch
do not expand to a value, but sometimes they insert some results in the current list. That is why you can use see the result from DTLfetch
in your document, but it does not work inside FPeval
.
To fix this, you can use a variant DTLfetchsave
of DTLfetch
which egreg has written for retrieving substring of `DTLfetch`. It saves the result in a new macro, which can then be expanded (similar to FPeval
itself):
begin{filecontents*}{students.csv}
name,grade
Joe Bloggs,2.7
Jane Doe,1.0
John Smith,3.0
end{filecontents*}
documentclass{article}
usepackage{datatool,fp}
% From egreg at https://tex.stackexchange.com/questions/335483/retrieving-substring-of-dtlfetch
newcommand{DTLfetchsave}[5]{%
edtlgetrowforvalue{#2}{dtlcolumnindex{#2}{#3}}{#4}%
dtlgetentryfromcurrentrow{dtlcurrentvalue}{dtlcolumnindex{#2}{#5}}%
let#1dtlcurrentvalue
}
begin{document}
DTLloaddb{students}{students.csv}
DTLfetchsavegrade{students}{name}{Jane Doe}{grade}
FPevaldoublegrade{2*grade}
doublegrade
end{document}
Answered by Marcel Krüger on September 28, 2021
I also discovered
xDTLassignfirstmatch
in datatool
that seems to work the same as DTLfetch
, with expansion, and works great for me!
Answered by alex dinovitser on September 28, 2021
I had the same issue when trying to use data from a (CSV) database for plotting single values with TikZ/PGFPlots or for printing values using siunitx.
With this post I found out how to store all values from the database as (expanded) LaTeX variable named after the respective key:
documentclass[tikz]{standalone}
usepackage{siunitx}
usepackage{filecontents}
begin{filecontents*}{mydb.csv}
key;value
mykey;1.0
end{filecontents*}
% Relevant code below
usepackage{datatool}
DTLsetseparator{;}
DTLloaddb{mydb}{mydb.csv}
begin{document}
DTLforeach{mydb}{Key=key,Value=value}
{%
cslet{Key}{Value}%
}
DTLfetch{mydb}{key}{mykey}{value} works
% while $num{DTLfetch{mydb}{key}{mykey}{value}}$ fails
mykey prints the value for mykey, $num{mykey}$ also works
end{document}
However, loading multiple databases with similar keys would re-assign the same variables.
As a quick fix, I made DTLFetch
assign the values to variables named after a concatenation of database name and key and wrote a function to parse the latter:
documentclass[tikz]{standalone}
usepackage{siunitx}
usepackage{filecontents}
begin{filecontents*}{mydb.csv}
key;value
mykey;1.0
end{filecontents*}
% Relevant code below
usepackage{datatool}
DTLsetseparator{;}
DTLloaddb{mydb}{mydb.csv}
newcommand{getval}[2]{csname#1#2endcsname}
begin{document}
DTLforeach{mydb}{Key=key,Value=value}
{%
cslet{mydbKey}{Value}%
}
getval{mydb}{mykey} prints the value for mykey, $num{getval{mydb}{mykey}}$ also works
end{document}
Answered by F1iX on September 28, 2021
Get help from others!
Recent Questions
Recent Answers
© 2024 TransWikia.com. All rights reserved. Sites we Love: PCI Database, UKBizDB, Menu Kuliner, Sharing RPP