evadne

evadne

Explorer.DataFrame.from_csv problem

Hi all

I have some issues reading nanosecond precision timestamps in CSVs using latest explorer.

Repro as follows:

./script/ingestion_test.csv

datetime_ns
1738573413286629810

./script/ingestion_test.exs

Mix.install([
  :explorer
])

{options, _, _} = OptionParser.parse(System.argv(), strict: [path: :string])
{:ok, path} = Keyword.fetch(options, :path)

Explorer.DataFrame.from_csv(Path.relative_to_cwd(path), [
  infer_schema_length: 0,
  columns: [
    "datetime_ns"
  ],
  dtypes: [
    {"datetime_ns", {:naive_datetime, :nanosecond}}
  ]
])
|> IO.inspect()

Outcome:

$ elixir ./script/ingestion_test.exs --path ./script/ingestion_test.csv
{:error,
 %RuntimeError{
   message: "Polars Error: could not parse `1738573413286629810` as dtype `datetime[ns]` at column 'datetime_ns' (column number 1)\n\nThe current offset in the file is 12 bytes.\n\nYou might want to try:\n- increasing `infer_schema_length` (e.g. `infer_schema_length=10000`),\n- specifying correct dtype with the `dtypes` argument\n- setting `ignore_errors` to `True`,\n- adding `1738573413286629810` to the `null_values` list.\n\nOriginal error: ```could not find a 'date/datetime' pattern for '1738573413286629810'```"
 }}

Surely I’m missing something elementary?

https://www.unixtimestamp.com/ agrees the timestamp is good. But it won’t parse.

Many thanks in advance

elixir 1.17.2
erlang 27.0.1
explorer 0.10.1

Marked As Solved

evadne

evadne

{:ok, frame} = Explorer.DataFrame.from_csv(Path.relative_to_cwd(path), [
  infer_schema_length: 0,
  columns: [
    "datetime_ns"
  ],
  dtypes: [
    {"datetime_ns", {:u, 64}}
  ]
])

frame
|> Explorer.DataFrame.put("dataframe_ns", frame["datetime_ns"] |> Explorer.Series.cast({:naive_datetime, :nanosecond}))
|> IO.inspect()

=

#Explorer.DataFrame<
  Polars[1 x 2]
  datetime_ns u64 [1738573413286629810]
  dataframe_ns naive_datetime[ns] [2025-02-03 09:03:33.286629]
>

Also Liked

kevinschweikert

kevinschweikert

I think Explorer only supports NaiveDatetime. I made it work with this code in Livebook:

tmp_dir = System.tmp_dir!()
test_csv_path = Path.join(tmp_dir, "test.csv")

File.write!(test_csv_path, 
"""
datetime_ns
1738573413286629810
""")

df = Explorer.DataFrame.from_csv!(test_csv_path, [
  infer_schema_length: 0,
  columns: [
    "datetime_ns"
  ],
  dtypes: [
    datetime_ns: {:u, 64}
  ]
])

dt = df["datetime_ns"]
  |> Explorer.Series.transform(fn dns -> DateTime.from_unix!(dns, :nanosecond) end)


Explorer.DataFrame.put(df, "datetime_ns", dt)
billylanchantin

billylanchantin

@evadne Glad you figured it out :slight_smile:

FWIW I couldn’t get Polars to (which Explorer uses under the hood) to parse the timestamp directly either. So your cast approach is what I’d use too. I will throw a few more pointers out there.

DF.mutate/2 is nice because you don’t need to keep around the original column:

require Explorer.DataFrame, as: DF

path = "./ingestion_test.csv"

path
|> DF.from_csv!(dtypes: %{datetime_ns: :u64})
|> DF.mutate(datetime_ns: cast(datetime_ns, {:naive_datetime, :nanosecond}))
# #Explorer.DataFrame<
#   Polars[1 x 1]
#   datetime_ns naive_datetime[ns] [2025-02-03 09:03:33.286629]
# >

There is also the :lazy option. It will defer the computation so that you never create the intermediate column in the first place:

path
|> DF.from_csv!(dtypes: %{datetime_ns: :u64}, lazy: true)
|> DF.mutate(datetime_ns: cast(datetime_ns, {:naive_datetime, :nanosecond}))
|> DF.collect()
# #Explorer.DataFrame<
#   Polars[1 x 1]
#   datetime_ns naive_datetime[ns] [2025-02-03 09:03:33.286629]
# >

That option is only needed if you need to go real fast for some reason.

Also, we do have support for non-naive datetimes. But that doesn’t seem super relevant for this use case.

Where Next?

Popular in Questions Top

senggen
Erlang/OTP 25 [erts-13.2.2] [source] [64-bit] [smp:8:8] [ds:8:8:10] [async-threads:1] 15:22:35.803 [error] gen_event {lager_file_backend...
New
fireproofsocks
I’m working on defining a simple Ecto schema for a table (in PostGres), but I don’t see where I can define a column as NOT NULL. Conside...
New
script
If I have a string “1000 cfu/ml” . I want to remove the characters and / and space . So the string is like this "1000" What is the ...
New
mcarvalho
What is the difference between System.get_env and Application.get_env? For example, what are best practices to use one versus another.
New
mgjohns61585
Could someone help me? I'm making my first elixir program, number guessing game. I can't figure out how to convert the user's guess from ...
New
shahryarjb
Hello, I have map which I want to convert it to string like this: the map: %{last_name: "tavakkoli", name: "shahryar"} the string I ne...
New
vonH
When I run the Plug and I recompile I wind up having to use Ctrl C to quit iex and start again. Witht the help of rlwrap I can use the cu...
New
chewm
Hi guys, nice to meet you to the whole forum, I’m new here, I’m trying to configure visual studio code for elixir, right now the intellis...
New
chrisalley
ExUnit now has describe blocks which is a welcome addition coming from RSpec. In the docs, it states that nested hierarchies of describe ...
New
wernerlaude
In AR this is so simple @articles = current_user.articles How to do in Ecto? def index(conn, _params) do current_user = conn.assig...
New

Other popular topics Top

Qqwy
Update: How to use the Blogs &amp; Podcasts section You can post links to your blog posts or podcasts either in one of the Official Blog...
3268 119930 1237
New
pmjoe
I have a relationship of love and hate with Elixir. Lots of things are just absolutely right, but there are some things that are kind of ...
New
openscript
Hello! Sorry for this astonishing simple question, but I’m really stuck. I try to set up the intellij-elixir plugin, but I don’t know ho...
New
sergio
I couldn’t find any guides that worked well with Phoenix 1.6.0 and esbuild. I hope this helps people test the waters and eases you into t...
New
Jim
As a follow up to my earlier question: I have the code compiling and running but not getting a successful login from the rest server. ...
New
chrismccord
As promised, the first release candidate of Phoenix 1.3.0 is out! This release focuses on code generators with improved project structure...
New
rms.mrcs
Hi, I need to transform a list of numbers into a map where the keys are the indexes and the values are the original values of the list....
New
baxterw3b
Hi guys, i’m new in the Elixir world, and i have to say, that i love it! i’m having some problem to understand anonymous functions with ...
New
9mm
I am constructing a JSON object (map) and I need to conditionally set a field. I’m trying to write proper elixir-way code… and I’m at a l...
New
lanycrost
Hi everyone! I need implement if…else if…else condition from my elixir code, and anymore of this control flow structures not work proper...
New

We're in Beta

About us Mission Statement