【问题标题】:pagination with the python cmd module使用 python cmd 模块进行分页
【发布时间】:2009-09-05 01:31:11
【问题描述】:

我正在使用 cmd 模块制作 Python 应用程序的原型。

给用户的一些消息会很长,我想给它们分页。 将显示消息的前 10 行(或可配置的数量),按空格键将显示下一页,直到消息结束。

我不想在这里重新发明一些东西,有没有简单的方法来实现这个功能?

【问题讨论】:

    标签: python pagination cmd


    【解决方案1】:

    简单的事情就是在运行时通过“less”或类似的命令来管道你的脚本。

    这里有一个简单的方法,可以大致完成您想要的操作:

    def print_and_wait(some_long_message):
        lines = some_long_message.split('\n')
        i=0
        while i < len(lines):
            print '\n'.join(lines[i:i+10])
            raw_input("press enter to read more...")
            i += 10
    

    你也可以考虑使用诅咒。

    【讨论】:

    • 谢谢,但是通过 less 管道会阻止交互,这是 cmd 模块的目标。实现一个 curses 解决方案远远超出了我想用 cmd 模块构建的初稿。但是,您的 print_and_wait 解决方案是一个好的开始(虽然没有按原样工作)。
    【解决方案2】:

    正如 Yoni 上面所说的那样,正确的方法是提供一种打印方法,该方法可以在您正在运行的 cmd 实例中自动分页。 Cmd 的构造函数接受 stdin 和 stdout 参数。提供一个像标准输出一样工作并支持您的分页打印方法的对象。

    class PagingStdOut(object):
        def write(self, buffer, lines_before_pause=40):
            # do magic paging here...
    

    【讨论】:

      【解决方案3】:

      我也有同样的问题。 pydoc module 内置了一个寻呼机。我就这样合并了它(我觉得这很老套而且不令人满意……不过我愿意接受更好的想法)。

      我喜欢这样的想法,即如果有超过 x 个结果并且分页打开,它会自动分页,这是可以实现的,但在这里没有完成。

      import cmd
      from pydoc import pager
      from cStringIO import StringIO
      import sys
      
      PAGER = True
      class Commander(cmd.Cmd):
          prompt = "> "
          def do_pager(self,line):
              global PAGER
              line = line + " 1"
              tokens = line.lower().split()
              if tokens[0] in ("on","true","t", "1"):
                  PAGER = True
                  print "# setting PAGER True"
              elif tokens[0] in ("off","false","f","0"):
                  PAGER = False
                  print "# setting PAGER False"
              else:
                  print "# can't set pager:  don't know -> %s" % tokens[0]
      
          def do_demo(self,line):
              results = dict(a=1,b=2,c=3)
              self.format_commandline_results(results)
      
          def format_commandline_results(self,results):
              if PAGER:
                  ofh = StringIO()
              else:
                  ofh = sys.stdout
      
              for (k,v) in sorted(results.items()):
                  print >> ofh, "%s -> %s" % (k,v)
      
              if PAGER:
                  ofh.seek(0)
                  pager(ofh.read())
      
              return None
      
          def do_EOF(self,line):
              print "",
              return True
      
      if __name__ == "__main__":
          Commander().cmdloop("# try: \n> pager off \n> demo \n> pager on \n> demo \n\n")
      

      【讨论】:

        【解决方案4】:

        分页子例程可以在IPythongenutils.py 文件中找到(参见pagepage_dumb 以获得更简单的一个)。代码有点复杂,但如果你想移植到包括 Windows 和各种终端仿真器在内的系统上,这可能是不可避免的。

        【讨论】:

        • 谢谢,我已经实现了我的分页例程。我会看看你指出的文件中我错过了什么。目前它可以在我的操作系统中运行,但我没有测试其他任何东西,因此便携式增强功能可能很有用。
        猜你喜欢
        • 2017-11-24
        • 2017-01-10
        • 1970-01-01
        • 1970-01-01
        • 2016-08-27
        • 1970-01-01
        • 2016-02-29
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多