Problem with HackerRank Elixir challenge

Yesterday I decided to join HackerRank and start doing the challenges in the Functional Programming section as a way to keep learning more Elixir.

Rather than call my initial function, HackerRank sends along all the params via input text (line by line by line). So rather than focusing on writing functions to solve the main problem, I spend my time trying to get all the input and put it together in a usable form so I can them start the challenge.

I’m just wondering if anyone has any tips for handling this issue.

Here’s a link to an example:

I ended up creating a function to just read line input until :eof, but I’m going to have to tweak it for each problem and that seems a bit odd to me.

Thought I’d ask just in case I’m missing something. I just started so I don’t know if the whole site is this way or not. I like Exercism.io more, but I’m always on the lookout for sites to do some challenges as a break from the norm.

Thanks!

2 Likes

HackerRank was one of the sites I started with, but starting from scratch with the input parser for every exercise, as well as beeing forced to develop on their site were the main showstoppers for me.

I left any similar site after I found exercism.io where I was able to develop with any IDE I like.

Also it feels as if my voice as a community member is much more valuable than in other sites of this kind, just because exercism.io is open source.

6 Likes

I’m using HackerRank to practice a little and I use this function to get the input:

def get_input do
  IO.gets("")
  |> String.trim
  |> String.split
end

I’m saving my solutions here. Feel free to compare solutions or give some refactoring tips for me :smile:

I typically create a couple helper functions.

def read_int do
  IO.gets("") |> String.trim |> String.to_integer
end

def read_int_list do
  IO.gets("") |> String.trim |> String.split(" ") |> Enum.map(&String.to_integer/1)
end

For the Armies puzzle, I used the following to try and optimize the IO. However, I was never able to get all test cases passing without timeouts and I gave up.

  def run do
    [[army_cnt, _]| queries] = read_file()
    output = 
      queries
      |> solve(army_cnt)
      |> Enum.join("\n")
    IO.write(:stdio, output)
  end

  def read_file do
    Enum.map(IO.stream(:stdio, :line), fn line ->
      line
      |> String.trim
      |> String.split(" ", trim: true)
      |> Enum.map(&String.to_integer/1)
    end)
  end
1 Like

I’ve only been playing with HR for a couple of days, but the below function has been working for me in most instances (though it may well be suboptimal). It translates an input of integers on an arbitrary number of lines into function arguments (I’ve used hd/1, tl/1, etc. to parse the lines into specific args). I then just pass the input to a main function that carries out the problem-specific logic. (And of course, I’ve occasionally tweaked Solution.input/0 for specific problems’ needs, e.g. calling Enum.map(&String.to_float/1) at the end instead.)

defmodule Solution
  def input do
      IO.stream(:stdio, :line)
      |> Enum.to_list
      |> Enum.map(&String.trim/1)
      |> Enum.map(&String.to_integer/1)
    end

  def main(list) do
    # code goes here
  end
end

Solution.input |> Solution.main

I would note that at least one of the first HR problems seems broken for Elixir – the problem asks you to output an arbitrary list of length n but two of the test cases erroneously require an output of the input integer n. Someone pointed this out 10 months ago, but it was never fixed (and the admin response suggested, at least to me, that the admin didn’t really understand Elixir as a language) – which does not inspire confidence in HR (so maybe exercism.io and/or codewars.com would be better…).

3 Likes