Advertisement
Guest User

脚注位置修复机器

a guest
Oct 11th, 2020
61
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 3.59 KB | None | 0 0
  1. from time import time
  2. from textwrap import fill
  3.  
  4. from pywikibot import Site, Page, warning
  5. from pywikibot.bot import SingleSiteBot, ExistingPageBot, NoRedirectPageBot
  6. from pywikibot.editor import TextEditor
  7.  
  8.  
  9.  
  10. class ReferenceFixer(
  11.     SingleSiteBot,
  12.     ExistingPageBot,
  13.     NoRedirectPageBot
  14. ):
  15.     def __init__(self, **kwargs):
  16.         super().__init__()
  17.         self.generator = self.site.randompages()
  18.  
  19.     def longpages(self):
  20.         for tup in self.site.longpages():
  21.             yield tup[0]
  22.  
  23.     def treat_page(self):
  24.         page = self.current_page
  25.         self.put_current(fix(page.text),
  26.             summary='同一个句子可能出现多个需要添加脚注的词语,因此请不要将脚注置于标点符号后面。请参阅[[Help:脚注]]。')
  27.  
  28.     def skip_page(self, page):
  29.         if not page.namespace().content:
  30.             return True
  31.         return super().skip_page(page)
  32.  
  33. def fix(text):
  34.     cur = Cursor(text)
  35.     while cur.find_next('。<ref'):
  36.         dist_tag = cur.next('</ref>', True)
  37.         dist_sct = cur.next('/>', True) # self-closing tag
  38.         if not dist_tag and not dist_sct:
  39.             cur.fwd(1)
  40.             continue
  41.         if bool(dist_tag) != bool(dist_sct):
  42.             dist = dist_tag or dist_sct
  43.         else:
  44.             dist = min(dist_tag, dist_sct)
  45.         cur.remove()
  46.         cur.to(dist)
  47.         if cur.next_nchars(1) == '。':
  48.             continue
  49.         cur.insert('。', pos=cur.pos())
  50.     return str(cur)
  51.  
  52. class Cursor:
  53.     def __str__(self):
  54.         return self.text
  55.  
  56.     def __init__(self, text, pos=0):
  57.         self.text = text
  58.         self._pos = pos
  59.  
  60.     def _out_of_range(self, num):
  61.         return num < 0 or num >= len(self.text)
  62.  
  63.     def pos(self):
  64.         return self._pos
  65.  
  66.     def at(self, pos):
  67.         if self._out_of_range(pos):
  68.             return False
  69.         else:
  70.             return self.text[pos]
  71.  
  72.     def this(self):
  73.         return self.text[self._pos]
  74.  
  75.     def next_nchars(self, count, this=False):
  76.         return (self.this() if this else '') + self.text[self._pos + 1:self._pos + count + 1]
  77.  
  78.     def to(self, pos):
  79.         if self._out_of_range(pos):
  80.             return False
  81.         else:
  82.             self._pos = pos
  83.             return True
  84.  
  85.     def fwd(self, count):
  86.         return self.to(self._pos + count)
  87.  
  88.     def back(self, count):
  89.         return self.to(self._pos - count)
  90.  
  91.     def insert(self, char, pos=None):
  92.         _pos = self._pos
  93.         text = self.text
  94.         if pos == None:
  95.             self.text = text[:_pos] + char + text[_pos:]
  96.         else:
  97.             self.text = text[:pos] + char + text[pos:]
  98.  
  99.     def remove(self, pos=None):
  100.         _pos = self._pos
  101.         text = self.text
  102.         if pos == None:
  103.             if self._out_of_range(_pos):
  104.                 return False
  105.             self.text = text[:_pos] + text[_pos + 1:]
  106.             return True
  107.         else:
  108.             if self._out_of_range(pos):
  109.                 return False
  110.             if pos < _pos:
  111.                 self._pos -= 1
  112.             self.text = text[:pos] + text[pos + 1:]
  113.             return True
  114.  
  115.     def next(self, sub, last_char=False):
  116.         if (result := self.text.find(sub, self._pos)) == -1:
  117.             return False
  118.         if last_char:
  119.             result += len(sub) - 1
  120.         return result
  121.  
  122.     def find_next(self, sub, to_last_char=False):
  123.         if not (pos := self.next(sub, to_last_char)):
  124.             return False
  125.         self.to(pos)
  126.         return True
  127.  
  128. def main():
  129.     ReferenceFixer().run()
  130.  
  131. if __name__ == "__main__":
  132.     main()
  133.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement