gpt4 book ai didi

elixir - 使用 xmerl 读取大型 XML 文件会导致节点崩溃

转载 作者:行者123 更新时间:2023-12-04 08:08:19 30 4
gpt4 key购买 nike

我有以下代码可以读取维基百科转储文件(~50 GB)并根据要求提供页面:

defmodule Pages do
def start_link(filename) do
pid = spawn_link(__MODULE__, :loop, [filename])
Process.register(pid, :pages)
pid
end

def next(xml_parser) do
send(xml_parser, {:get_next, self()})
receive do
{:next_page, page} -> page
end
end

def loop(filename) do
:xmerl_sax_parser.file(filename,
event_fun: &event_fun/3,
event_state: :top)
loop_done
end

defp loop_done do
receive do
{:get_next, from} -> send(from, {:next_page, nil})
end
loop_done
end

defp event_fun({:startElement, _, 'page', _, _}, _, :top) do
:page
end

defp event_fun({:startElement, _, 'text', _, _}, _, :page) do
:text
end

defp event_fun({:characters, chars}, _, :text) do
s = List.to_string(chars)
receive do
{:get_next, from} -> send(from, {:next_page, s})
end
:text
end

defp event_fun({:endElement, _, 'text', _}, _, :text) do
:page
end

defp event_fun({:endElement, _, 'page', _}, _, :page) do
:top
end

defp event_fun({:endDocument}, _, state) do
receive do
{:get_next, from} -> send(from, {:done})
end
state
end

defp event_fun(_, _, state) do
state
end
end

由于代码使用 SAX解析器我希望持续的内存占用。当我尝试使用阅读前 2000 页时
Enum.each(1..2000, fn(x) -> Pages.next(Process.whereis(:pages)); end)
:pages流程用途 1,1 GB内 stub 据 :observer.start() .当我尝试阅读 10000 页时,整个事情崩溃了:
Crash dump is being written to: erl_crash.dump...done
eheap_alloc: Cannot allocate 5668310376 bytes of memory (of type "heap").

当我打开 erl_crash.dump使用转储查看器我看到以下内容:
enter image description here

上面的代码有问题吗? GC 不够快?虽然我可以看到每个进程的内存,但它并没有告诉我很多。我怎样才能看到这个内存实际上去了哪里?

附言这是今天的故障转储链接: https://ufile.io/becba .
原子数为14490, MsgQ :pages 为 2所有其他进程为 0。

最佳答案

默认的最大原子数略高于 1 million atoms .鉴于英文维基百科has over 5 million articlesxmerl seems to create an atom for each namespace URI ,我想这可能是罪魁祸首。

此外,在 Elixir 上尝试下面的代码失败,只是一个“堆栈粉碎错误”。

Enum.each(1..2000000, fn (x) ->
x
|> Integer.to_string
|> String.to_atom
end)

但是,如果我使用环境变量 ELIXIR_ERL_OPTIONS="+t 5000000" 将原子限制提高到 500 万左右。 ,问题消失。

关于elixir - 使用 xmerl 读取大型 XML 文件会导致节点崩溃,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39018108/

30 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com