调用timer.tc会导致SystemLimitError的原因?

问题描述 投票:0回答:1

我正在Elixir中编写一个简单的模块,该模块将数据加载到用Erlang编写的gen_server中。我需要测量加载操作的时间,而这正是我遇到的问题。当我在第46行(带有crateStations的那个)上调用:timer.tc()时,出现SystemLimitError,我不知道是什么会导致这种行为,因此不胜感激。波纹管是所使用的elxir模块的代码,我以前使用过Erlang gen_server,没有发生此类错误。

defmodule Data do

  defp nameStation({:cords,lat,lang}) do
    "station_#{lang}_#{lat}}}"
  end

  defp identifyStations(data) do
    data |> Enum.map((&(&1.location))) |> Enum.uniq |> Enum.map((fn({lat,lang})->{:cords,lat,lang}end))
  end

  defp createStations(data)do
    identifyStations(data) |>
    Enum.each((fn (cords)->:pollution_gen_server.addStation(nameStation(cords),cords) end))
  end

  defp createMesurements(data) do
    data |> Enum.each((fn(value)->
                       :pollution_gen_server.addValue(value.location,value.datetime,"PM10",value.pollutionLevel ) end))
  end

  defp importLinesFromCSV(path) do
    File.read!(path) |> (&(String.split(&1, "\r\n"))).()
  end

  defp parse(line) do
    [date_l,time_l,lang_l,lat_l,polltion_l] = String.split(line,",")
    lat = lat_l |> Float.parse() |> elem(0)
    lang = lang_l |> Float.parse() |> elem(0)
    pollution = polltion_l |> Integer.parse() |> elem(0)
    {hours,mins} = time_l |> String.split(":")  |> Enum.map(&(Integer.parse/1)) |>Enum.map(&(elem(&1,0))) |>
           :erlang.list_to_tuple()
    date = date_l |>  String.split(":") |> Enum.map(&(Integer.parse/1)) |> Enum.reverse() |>Enum.map(&(elem(&1,0))) |>
           :erlang.list_to_tuple()
    %{
      :datetime => {date,{hours,mins,0}},
      :location => {lat,lang},
      :pollutionLevel => pollution
    }
  end


  def run(path) do
    :pollution_sup.start_link()
    lines = importLinesFromCSV(path) |> Enum.map(&parse/1)

    time_stations = :timer.tc(&createStations/1,lines) |> elem(0) |> Kernel./(1_000_000)
    time_measurements = :timer.tc(&createMesurements/1,lines) |> elem(0) |> Kernel./(1_000_000)

    time_mean = :timer.tc(&:pollution_gen_server.getStationMean/2,["PM10",{:cords, 49.986, 20.06}]) |> elem(0) |> Kernel./(1_000_000)
    mean = :pollution_gen_server.getStationMean("PM10",{:cords, 49.986, 20.06})

    time_daily = :timer.tc(&:pollution_gen_server.getDailyMean/2,["PM10",{2017, 5, 3}]) |> elem(0) |> Kernel./(1_000_000)
     daily = :pollution_gen_server.getDailyMean("PM10",{2017, 5, 3})

     IO.puts "Time of loading stations: #{time_stations}"
     IO.puts "Time of loading mesurements: #{time_measurements}"

     IO.puts "Time of getting mean: #{time_mean} result: #{mean}"
     IO.puts "Time of getting daily: #{time_daily} result: #{daily}"
  end

end
erlang elixir otp erl
1个回答
0
投票

调用:pollution_gen_server.addStation(nameStation(cords),...)是否从名称创建原子?在这种情况下,您可能会溢出原子表,该原子表默认情况下可容纳1048576个唯一原子(即,刚好超过一百万)。如果无法重写代码,则可以在启动系统时尝试使用+t标志提高级别。

最新问题
© www.soinside.com 2019 - 2024. All rights reserved.