Ответ 1
Попробуйте следующее:
(defun replace-in-string (what with in)
(replace-regexp-in-string (regexp-quote what) with in nil 'literal))
Я ищу эквивалент replace-regexp-in-string
, который просто использует литеральные строки, никаких регулярных выражений.
(replace-regexp-in-string "." "bar" "foo.buzz") => "barbarbarbarbarbarbarbar"
Но я хочу
(replace-in-string "." "bar" "foo.buzz") => "foobarbuzz"
Я пробовал различные функции replace-*
, но не могу понять.
Edit
В ответ на сложные ответы я решил сравнить их (да, я знаю, что все тесты ошибочны, но это все еще интересно).
Выходной сигнал benchmark-run
равен (time, # garbage collections, GC time)
:
(benchmark-run 10000
(replace-regexp-in-string "." "bar" "foo.buzz"))
=> (0.5530160000000001 7 0.4121459999999999)
(benchmark-run 10000
(haxe-replace-string "." "bar" "foo.buzz"))
=> (5.301392 68 3.851943000000009)
(benchmark-run 10000
(replace-string-in-string "." "bar" "foo.buzz"))
=> (1.429293 5 0.29774799999999857)
replace-regexp-in-string с цитируемыми regexp-победами. Временные буферы делают замечательно хорошо.
Изменить 2
Теперь с компиляцией! Придется делать 10-кратную итерацию:
(benchmark-run 100000
(haxe-replace-string "." "bar" "foo.buzz"))
=> (0.8736970000000001 14 0.47306700000000035)
(benchmark-run 100000
(replace-in-string "." "bar" "foo.buzz"))
=> (1.25983 29 0.9721819999999983)
(benchmark-run 100000
(replace-string-in-string "." "bar" "foo.buzz"))
=> (11.877136 86 3.1208540000000013)
haxe-replace-string выглядит хорошо
Попробуйте следующее:
(defun replace-in-string (what with in)
(replace-regexp-in-string (regexp-quote what) with in nil 'literal))
s.el
библиотека обработки строк имеет s-replace
:
(s-replace "." "bar" "foo.buzz") ;; => "foobarbuzz"
Я рекомендую установить s.el
из диспетчера пакетов Emacs, если вы работаете со строками в своем Elisp.
Я бы не надеялся, что это будет быстрее:
(defun haxe-replace-string (string string-a string-b)
"Because there no function in eLisp to do this."
(loop for i from 0 upto
(- (length string) (length string-a))
for c = (aref string i)
with alen = (length string-a)
with result = nil
with last = 0
do (loop for j from i below (+ i alen)
do (unless
(char-equal
(aref string-a (- j i))
(aref string j))
(return))
finally
(setq result
(cons (substring string last (- j alen)) result)
i (1- j) last j))
finally
(return
(if result
(mapconcat
#'identity
(reverse (cons (substring string last) result)) string-b)
string))))
Becasue replace-regexp-in-string
- это нативная функция, но вы никогда не знаете... В любом случае, я написал это некоторое время назад по какой-то причине, поэтому, если вы заполните как сравнение производительности - вы можете попробовать:)
Другая идея, использующая временный буфер:
(defun replace-string-in-string (what with in)
(with-temp-buffer
(insert in)
(beginning-of-buffer)
(while (search-forward what nil t)
(replace-match with nil t))
(buffer-string)))