【问题标题】:StringScanner scanning IO instead of a stringStringScanner 扫描 IO 而不是字符串
【发布时间】:2011-01-28 09:06:08
【问题描述】:

我有一个使用 ruby​​ 的标准 StringScanner 编写的解析器。如果我可以在流文件上使用它会很好。是否有不需要我将整个字符串加载到内存中的等效于 StringScanner 的方法?

【问题讨论】:

    标签: ruby io


    【解决方案1】:

    StringScanner 是为此而设计的,加载一个大字符串并使用内部指针来回移动,如果你把它变成一个流,那么引用就会丢失,你不能使用 unscancheck_untilpre_matchpost_match、 你可以,但为此你需要缓冲所有先前的输入。

    如果您担心缓冲区大小,则只需按数据块加载,并使用简单的正则表达式或名为 Parser 的 gem。 最简单的方法是读取固定大小的数据。

    # iterate over fixed length records
    open("fixed-record-file") do |f|
      while record = f.read(1024)
        # parse here the record using regexp or parser
      end
    end
    

    [更新]

    即使使用此循环,您也可以使用 StringSanner,您只需使用每个新数据块更新字符串:

    string=(str)

    将正在扫描的字符串更改为 str 并重置扫描仪。 返回字符串

    【讨论】:

    • 对 Parser gem 的引用(whitequark/parser 无关紧要,因为 Parser 是一个 Ruby 解析器(在 Ruby 中)。
    【解决方案2】:

    有StringIO。

    抱歉误读了您的问题。看看this好像有流媒体选项

    【讨论】:

    • 这与我需要的相反!
    • 抱歉误读了您的问题。看看tinyurl.com/ydrq8o8似乎有流媒体选项。
    【解决方案3】:

    您可能需要稍微修改一下解析器,但您可以像这样将文件中的行输入扫描仪:

    File.open('filepath.txt', 'r') do |file|
      scanner = StringScanner.new(file.readline)
      until file.eof?
        scanner.scan(/whatever/)
        scanner << file.readline
      end
    end
    

    【讨论】:

    • 我知道这是几年后的事了,但这仍然会将整个文件读入内存。一旦你到达 eof,“扫描仪”就会保存文件的完整副本......(在字符串指针移过内容后它不会释放任何内容)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-08-12
    • 2023-03-30
    • 2021-03-19
    • 1970-01-01
    • 2023-03-24
    • 1970-01-01
    相关资源
    最近更新 更多