2012-09-06 35 views
2

這是我有:左邊最小的匹配表達式?

{a} {b} over {c} {d} 
{a} {{b} over {c}} {d} 

(我有一些文字,它有這樣的表情)我想都轉換爲:

​​

這裏是我最好的選擇:

(goto-char (point-min)) 
(while (search-forward-regexp "{+?\\(.+?\\)} +over +{\\(.+?\\)}+?" nil t) 
    (replace-match (concat "\\\\" "frac{\\1}{\\2}") t nil)) 

但它不起作用。我得到:

\frac{a} {b}{c} {d} 
\frac{a} {{b}{c}} {d} 

分別。

問題是 - 我的正則表達式儘可能地捕獲左邊。儘管我需要它儘可能少地捕捉。

編輯

接受的答案不適用於更復雜的情況下工作(這也是我需要):

{d^{2} q} over {d t^{2} } 
{{d^{2} q} over {d t^{2} }} 

這裏(因爲嵌套的)是一個工作版本解析器(代碼的有趣部分從while開始):

(defun over2frac() 
    (interactive) 
    (let (start end 
     (case-fold-search nil) 
     lStart lEnd lStr 
     rStart rEnd rStr) 
    (if (use-region-p) 
     (progn (setq start (region-beginning)) ;; then 
       (setq end (region-end))) 
     (progn (setq start (line-beginning-position)) ;; else 
      (setq end (line-end-position)))) 
    (save-restriction 
     (narrow-to-region start end) 
     (goto-char (point-min)) 

     (while (search-forward-regexp "{\\(.+\\)}\s*over\s*{\\(.+?\\)}" nil t) 

     ;; r: 
     (goto-char (match-beginning 2)) 
     (backward-char 1) 
     (setq rStart (point)) 
     (forward-sexp) 
     (setq rEnd (point)) 
     (setq rStr (buffer-substring-no-properties rStart rEnd)) 

     ;; l: 
     (goto-char (match-end 1)) 
     (forward-char) 
     (setq lEnd (point)) 
     (backward-sexp) 
     (setq lStart (point)) 
     (setq lStr (buffer-substring-no-properties lStart lEnd)) 

     (delete-region lStart rEnd) 
     (insert "\\" "frac" lStr rStr) 
     )))) 

由於它採用forward-sexpbackward-sexp - 並沒有定義syntax-table - 它只能在適當的方式(如rst-modetext-mode - 但不是emacs-lisp-mode。對於上述複雜的例子它給出:

\frac{d^{2} q}{d t^{2} } 
{\frac{d^{2} q}{d t^{2} }} 

編輯2

(defun backslash-func--args-on-both-sides (Find Replace) 
    (goto-char (point-min)) 
    (while (search-forward-regexp (concat "\\([^{]+\\)}\s*" Find "\s*{\\([^}]+\\)") nil t) 

    ;; r: 
    (goto-char (match-beginning 2)) 
    (backward-char 1) 
    (setq rStart (point)) 
    (forward-sexp) 
    (setq rEnd (point)) 
    (setq rStr (buffer-substring-no-properties rStart rEnd)) 

    ;; l: 
    (goto-char (match-end 1)) 
    (forward-char) 
    (setq lEnd (point)) 
    (backward-sexp) 
    (setq lStart (point)) 
    (setq lStr (buffer-substring-no-properties lStart lEnd)) 

    ;; s: 
    (goto-char lStart) 
    (if (looking-back "{") 
     (setq lStart (1- (point)))) 

    (goto-char rEnd) 
    (if (looking-at "}") 
     (setq rEnd (1+ (point)))) 

    (delete-region lStart rEnd) 
    (insert "\\" Replace lStr rStr)) 

    (goto-char (point-min)) 
    (while (search-forward-regexp (concat "\\([0-9a-zA-Z_^]+\\)\s*" Find "\s*\\([0-9a-zA-Z_^]+\\)") nil t) (replace-match (concat "\\\\" Replace "{\\1}{\\2}") t nil)) 
) 

此轉換兩件事:

{d^{2} q} over {d t^{2} } 
{{d^{2} q} over {d t^{2} }} 

\frac{d^{2} q}{d t^{2} } 

我在這裏並沒有使用let,因爲所有的變種都已經在本地了 - 而且defun本身就在另一個defun中。 Full code

+0

當然,它本來就容易只寫兩個正則表達式,因爲一個只需要輕微從另一個修改。 – Squidly

回答

3

使用該表達式:http://regex101.com/r/kY8jY5

/{+([^{}]+)}\s*over\s*{([^{}]+)}+/g

表達應與emacs的兼容。

替換:

\frac{\1}{\2}

注:我不確定,如果你在Emacs中使用\1$1

+1

在emacs中:'(while(search-forward-regexp){+ \\([^ {}] + \\)} \ s * over \ s * {\\([^ {}] + \\ )} +「nil t)(replace-match(concat」\\\\「」frac {\\ 1} {\\ 2}「)t nil))'。這是我使用'{(。+?)}'而不是'([^ {}] +)''的壞習慣。 – Adobe

0

通過增加一個貪婪*在正則表達式的開始,並把它先在更換:

(goto-char (point-min)) 
(while (search-forward-regexp "\\(.*\\){+?\\(.+?\\)} +over +{\\(.+?\\)}+?" nil t) 
    (replace-match (concat "\\1\\\\" "frac{\\2}{\\3}") t nil)) 

我得到了它產生這樣的:

{a} \frac{b}{c} {d} 
{a} {\frac{b}{c}} {d} 

我不知道如果有任何辦法擺脫周邊{}多餘的......

+0

無論如何 - 我喜歡在左邊儘可能多的捕捉想法。 – Adobe

相關問題