I thought (defun string-integer-p (string)
was cool,
I found it in the emacswiki.
Is there a variant of it I can use to test if string contains float eg. "8.3"
I thought (defun string-integer-p (string)
was cool,
I found it in the emacswiki.
Is there a variant of it I can use to test if string contains float eg. "8.3"
Since one can edit program texts in many programming languages with emacs it is important to note that the floating point syntax can vary with the programming language. For an instance 1.2d3
is a floating point number in Fortran but not in Elisp.
In the following I present a function my-string-float-p
that returns t
if the whole string is read as a floating point number by the Elisp reader.
One can interpret the first object in the string as lisp by read
and
test this object with floatp
.
If read
has gobbled all characters from the string that is the only
thing represented by the string.
(defun my-string-float-p (str)
"Non-nil if string STR represents a floating point number."
(with-temp-buffer
(insert str)
(goto-char (point-min))
(condition-case nil
(and (floatp (read (current-buffer)))
(eobp))
(error nil))))
Test suite:
(my-string-float-p "x")
nil
(my-string-float-p "0")
nil
(my-string-float-p "0.0")
t
(my-string-float-p "8.3")
t
(my-string-float-p "0.1Hello")
nil
(my-string-float-p "0.1 Hello")
nil
(my-string-float-p "(")
nil
(my-string-float-p ")")
nil
(defun f (s) (floatp (read s)))
does the same thing for a string arg, no? At least for your test suite it seems to.
– Drew
Jul 09 '18 at 14:55
(my-string-float-p "0.1 Hello")
which does not return the expected nil
with (f "0.1 Hello")
and your (defun f (s) (floatp (read s)))
.
– Tobias
Jul 09 '18 at 15:00
I think string-to-number
is usable here. It has the unfortunate property that it returns 0
for non-numeric strings (an option to return nil
would seem sensible, especially as that's what its helper actually does); however 0
is not a float, so...
(defun my-string-float-p (str)
"Non-nil if string STR represents a floating point number."
(floatp (string-to-number str)))
(my-string-float-p "x")
nil
(my-string-float-p "0")
nil
(my-string-float-p "0.0")
t
my-string-float-p
gives t
for (my-string-float-p "0.1Hello")
. Is that intended behavior?
– Tobias
Jul 09 '18 at 07:51
(string-to-number "0.1Hello")
returns 0.1
. It's documented (trailing chars are ignored), so it's "intended" in that respect. Whether it's useful behaviour rather depends on your use-case. Thanks for pointing it out.
– phils
Jul 09 '18 at 10:20
(defun string-float-p (str)
"Non-nil if string STR represents a floating point number."
(let ((rd (read-from-string str)))
(and (floatp (car rd)) (eq (cdr rd) (length str)))))
(condition-case nil ... (error nil))
.
– Tobias
Jul 09 '18 at 18:59
(let ((rd (read (concat "(" str ")")))) (and (floatp (car rd)) (null (cdr rd))))
. That version would ignore spaces at front and tail of str
.
– Tobias
Jul 09 '18 at 19:02
(defun string-float-p (string) (if (string-match "\\
[-+]?[0-9]+\.[0-9]*\'" string) t nil))` -- https://www.emacswiki.org/emacs/ElispCookbook – lawlist Jul 08 '18 at 22:40string-integer-p
in the question, or at least link to the wiki page that defines it. – Drew Jul 09 '18 at 00:48