[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: More Regexp help
From: |
Aaron Hill |
Subject: |
Re: More Regexp help |
Date: |
Sat, 27 Jun 2020 22:04:49 -0700 |
User-agent: |
Roundcube Webmail/1.4.2 |
On 2020-06-27 6:45 pm, Freeman Gilmore wrote:
I have a string of accidentals and I want the sum of their deviation.
If I have the string, “a bx3 cd -jk -DRx2 rtyu -HJK 31 17x4 -7 -41x3”
with
all possible examples.
I want to convert it to, “ a (* b 3) -jk (* -DR 2) rtyu -HJK n31 (*
n17
4) -n7 (* -n41 3)”
Then, (a (* b 3) -jk (* -DR 2) rtyu -HJK n31 (* n17 4) -n7 (* -n41
3)) .
( + will be applied to this)
1] Where “a” “cd” “-jk” “rtyu” “-HJK” are unchanged. (variables)
2] Numbers “31” “17x4” “-7” “-41x3” have “n” prefixed to them like,
“n31”
“n17x4” “-n7” “-n41x3”. (numbers converted to variables)
3] And “bx3” “-DRx2” “17x4” “-41x3” become “(* b 3)” “(* -DR 2)” “(*
n17
4)” “(* -n41 3)”. (number of times variables are used)
This is way beyond my capability, and I would appreciate help with
this.
For my simple mind it would teach me more if this were done in say 3
steps
rather than mapped.
-----------------------------------------------------
Broken into individual steps, as you have requested:
;;;;
(use-modules (ice-9 regex))
(define string "a bx3 cd -jk -DRx2 rtyu -HJK 31 17x4 -7 -41x3")
(format #t "\n[1] ~s" string)
(set! string
(regexp-substitute/global #f
"(^|\\s)(-?)([0-9]+)"
string
'pre 1 2 "n" 3 'post))
(format #t "\n[2] ~s" string)
(set! string
(regexp-substitute/global #f
"(^|\\s)(\\S+)(x([0-9]+))"
string
'pre 1 "(* " 2 " " 4 ")" 'post))
(set! string (string-append "(" string ")"))
(format #t "\n[3] ~s" string)
(define expr (with-input-from-string string read))
(format #t "\n[4] ~s" expr)
;;;;
====
[1] "a bx3 cd -jk -DRx2 rtyu -HJK 31 17x4 -7 -41x3"
[2] "a bx3 cd -jk -DRx2 rtyu -HJK n31 n17x4 -n7 -n41x3"
[3] "(a (* b 3) cd -jk (* -DR 2) rtyu -HJK n31 (* n17 4) -n7 (* -n41
3))"
[4] (a (* b 3) cd -jk (* -DR 2) rtyu -HJK n31 (* n17 4) -n7 (* -n41 3))
====
---------------------------------------------------------------
Processed in a single logical operation, as I would recommend:
;;;;
(use-modules (ice-9 regex))
(define string "a bx3 cd -jk -DRx2 rtyu -HJK 31 17x4 -7 -41x3")
(format #t "\n[1] ~s" string)
(define expr
(map (lambda (m)
(let* ((prefix (match:substring m 1))
(digits (match:substring m 3))
(letters (match:substring m 4))
(count (match:substring m 6))
(name (or letters (string-append "n" digits)))
(symbol (string->symbol (string-append prefix name))))
(if count
(list '* symbol (string->number count))
symbol)))
(list-matches
"(-?)(([0-9]+)|([A-Za-z]+))(x([0-9]+))?"
string)))
(format #t "\n[2] ~s" expr)
;;;;
====
[1] "a bx3 cd -jk -DRx2 rtyu -HJK 31 17x4 -7 -41x3"
[2] (a (* b 3) cd -jk (* -DR 2) rtyu -HJK n31 (* n17 4) -n7 (* -n41 3))
====
NOTE: In both cases above, I stopped short of evaluating the expression,
as there would be a whole host of unbound variables. Assuming a valid
environment, the summation could be computed as easily as:
(primitive-eval (cons '+ expr))
-- Aaron Hill
- More Regexp help, Freeman Gilmore, 2020/06/27
- Re: More Regexp help,
Aaron Hill <=