Erlang - C and Erlang

2019-03-28 11:34发布

问题:

There are certain common library functions in erlang that are much slower than their c equivalent.

Is it possible to have c code do the binary parsing and number crunching, and have erlang spawn processes to run the c code?

回答1:

Of course C would be faster, in the extreme case, after optimizations. If by faster you mean faster to run.

Erlang would be by far, faster to write. Depending on the speed requirements you have Erlang is probably "fast enough", and it will save you days of searching for bugs in C.

C code will only be faster after optimizations. If you spend the same amount of time on C and Erlang you will come out with about the same speed (note that I count time spent debugging and error fixing in this time estimation. Which will be a lot less in Erlang).

So:

faster writing = Erlang
faster running (after optimisations) = C
faster running without optimisations = any of the two

Take your pick.



回答2:

There are two rough rules of thumb based on Erlang FAQ:

  1. Code which involves mainly number crunching and data processing will run about 10 times slower than an equivalent C program. This includes almost all "micro benchmarks".

  2. Large systems which spent most of their time communicating with other systems, recovering from faults and making complex decisions run at least as fast as equivalent C programs.

However there are some official solutions to the lack of number crunching performance of Erlang:

  • Native Implemented Function (NIF):

Implementing a function in C and loading its object code into Erlang virtual machine to be like a standard Erlang function but with native performance.

Examples: Evedis, Bitcask, ElevelDB

  • Port:

A byte-oriented interface from Erlang virtual machine to external OS processes through standard input and output file descriptors. The communication with this port is through message passing from Erlang's point of view.

  • Port Driver:

A dynamically linked C object file which is loaded into Erlang virtual machine and acts like a port. The communication with this port driver is through message passing from Erlang's point of view.

Examples: OTP_Inet, ENanomsg, P1_TLS

  • C Node:

You can simply promote your Erlang runtime to a distributed node. This way there is a specification to implement an Erlang runtime in C and communicate with Erlang nodes with a single interface.

All of aforementioned solutions have its own pros and cons and need to be used with extreme care.



回答3:

First of all write whole logic of the system in Erlang, then implement handling binaries in C. Using NIFs (it is kind of interface to C) is pretty straight forward and transparent to the rest of the system. Here is another thread about talking to C Run C Code Block in Erlang.

Before hacking C, make sure you benchmarked current implementation. It is possible that it will satisfy your needs especially with the latest Erlang/OTP release (R14) which introduces great enhancements to binary handling.



回答4:

easy threading is not so interesting to erlang. Easy threading + Message passing and the OTP framework is what's awesome about erlang. If you need number crunching use something like ocaml, python, haskell. Erlang is all that good at number crunching.

Parsing binaries is one of the things erlang is best at though, probably the best for it. Joe's book programming erlang covers everything really well, and is not so expensive used. It also talks about integrating C code and gives an example. the source is available from pragmatic programming without needing to buy the book, you can grep #include or something.



回答5:

If you really look for speed you should try OpenMP or MPI parallel programming frameworks for C and C++. I recommend you to take a look at Patterns for Parallel Programming (link to amazon.com) for the details of OpenMP and MPI programming patterns.

The section of erl_nif in Erlang ERTS reference manual will be helpful.



回答6:

If you like Erlang, but want C speed, why not go for JOCAML. It is an extension for OCAML (which is similar to Erlang but is near C in terms of speed) designed for the multicore revolution going on at the moment. I love it (and I know more than 10 programming languages...)



回答7:

Yes,

But there's more than one way to this, loosely speaking, some or all of which are already listed.

We should ask:

  • Are those procedures really equivalent (how do the Erlang and C differ)?
  • Is there a better way to write Erlang for this task (other procedures/libraries or data-types)?

It may be helpful to consider this post: Scaling & Speed with Erlang.



回答8:

To address the question, yes it is possible to have erlang call some c function to handle a specific task. The most common way is to use a NIF - http://erlang.org/doc/tutorial/nif.html. NIFs were recommended only for short running functions before Erlang version 20 or so, few ms, because they were blocking, which couldn't work with Erlangs preemptive scheduler. Now with dirty threads it is more flexible, you can read up on that.

Just to note, C may be faster at parsing binary, though you should run tests, Erlang is by far faster to write the code. Erlang does a great job parsing binaries by pattern matching.



回答9:

I used C over 20 years. I am using Erlang almost exclusively the recently years. C is faster to run for obvious reason. Hower, Erlang is fast enough for most things when you do it right. Also, writing Erlang is much faster and more of fun.

For the piece of algorithms for which the run-time speed is critical, it surely can be written in C, which is the way of Erlang BIFs.



标签: c++ c erlang