Fork me on GitHub
#clojure
<
2017-10-29
>
mingp01:10:20

For small and specifically performance-sensitive sections in a program, is it possible to write "imperative with local mutable variables" style code using Clojure? In other words, is it possible to "write Java in Clojure"? The closest thing I could find were volatiles, and those are still one extra layer of boxing, right?

mingp01:10:24

For what it's worth, I understand this goes heavily against the idioms of Clojure in the standard case.

the2bears01:10:01

@mingp, if you're thinking of writing "Java in Clojure", why not just write the Java code and call that? What I mean is, Java's a very good Java, if that's what you want 🙂

phronmophobic01:10:08

you can write “java in clojure”

mingp01:10:18

@the2bears Yes, that's the other option. Mainly, the benefit from a theoretical "Java in Clojure" would be locality/organization of the source files, for whatever that's worth.

phronmophobic01:10:48

depending on how much performance you need to eek out

phronmophobic01:10:42

most of the code I’ve seen that focuses on performance talks about type hints to avoid reflection which is one of the slower parts

mingp01:10:00

@smith.adriane I'm looking for on-par with writing regular imperative Java. Which is to say, I need mutable locals in an unboxed form.

phronmophobic01:10:16

are you creating lots of volatiles?

the2bears01:10:36

Yes, and using things like transient collections, as long as they don't leak outside the function.

phronmophobic01:10:37

you may be able to create them once and reuse them, depending on the context

mingp01:10:44

For now, it's purely hypothetical. I want to know if I have this option available before I get into it.

mingp01:10:14

Because, whether I do or don't have this option available will probably change what I do.

phronmophobic01:10:18

because other than creation, I think it’s the same as just regular java mutation

the2bears01:10:27

Can you be more clear by what you mean with "write Java in Clojure" though? There's a wide scope of what it could mean.

mingp01:10:13

@the2bears Say I take a generic computer algorithms textbook. It has well-known algorithms in a form that can be translated near-verbatim into Java, same as any other traditional imperative language. If I wanted to do the same for Clojure, and maintain Java-level performance, my (admittedly limited) understanding is that I would need mutable locals.

the2bears01:10:59

I see. I haven't tried (at least on purpose) to program imperatively in Clojure having spent so much energy to leave Java behind 🙂 I can't think of anything beyond mutability you'd need, it seems all flow control mechanisms are there.

mingp01:10:05

For the most part, I try to learn and write idiomatic Clojure. But for that low-single-digit percent of code that needs it, I'm exploring options for getting Java-level performance.

the2bears01:10:36

I'd just use Java for that.

mingp01:10:15

Yea, that makes sense.

noisesmith01:10:34

yeah - particularly because of the issues with boxed numerics, it's just easier to write a bit of java once you know which code has to be that fast

mingp01:10:45

@noisesmith True. Although, it seems like (from what I can tell from http://insideclojure.org/2014/12/15/warn-on-boxed/), unboxed math is possible in Clojure.

noisesmith01:10:17

it's possible, it's a pain to get right

mingp01:10:23

@the2bears @smith.adriane @noisesmith Well, thank you for your responses. I think I should go reconsider what I am doing and why, as it sounds like I may be entering "when all you have is a hammer" territory.

phronmophobic01:10:06

I think one of the nice things for clojure is that if you do want to use some of the great work in the jvm ecosystem, you can use it as needed

mingp01:10:42

So, I just went to look at the Benchmarks Game to see how they micro-optimized algorithms in Clojure. Unfortunately, it looks like, at some point recently, they removed Clojure from their languages list.

Alex Miller (Clojure team)03:10:09

Looks like it was removed from the web site on sept 20th, along with scala?

mingp03:10:48

@lovuikeng Looks like that one's full of dead links, unfortunately. I can click into the language pages, but not the implementation source code pages. It just returns 404 Not Found.

lovuikeng06:10:42

2016 clojure removed? Guess we'll have to wait until 2032... "abandoned in 2002...restarted in 2004...continued from 2008...Everything has changed; several times." https://benchmarksgame.alioth.debian.org/sometimes-people-just-make-up-stuff.html

vemv09:10:15

anyone know a handy way to detect circular dependencies in graphs?

vemv09:10:39

I took a look at ubergraph and loom, no luck

jeff.terrell16:10:18

By chance I happened across this yesterday: http://clj-me.cgrand.net/2013/03/18/tarjans-strongly-connected-components-algorithm/ It sounds like it's maybe not what you need, @U45T93RA6, but FYI just in case it's useful to you.

timrichardt09:10:03

should be translated to clojure very quickly

vemv09:10:45

can eventually try out, thanks! meanwhile checking if I can steal something off stuartsierra/component

vemv09:10:35

guess so! (def has-circular-dependencies? (complement dag?)) ?

leonoel10:10:42

yes, a dag has no cycle by definition

leonoel10:10:02

this function won't give you the culprit however

rovanion10:10:06

Does anyone know how to add accents or diacritical marks to characters? As in add ¨ to a to make ä?

rovanion10:10:56

Found that you can do "e\u0305".

metametadata11:10:36

https://github.com/funcool/clojure.jdbc Comparing to java.jdbc I like clearer docs and simpler API, especially that there's a difference between connections/dbspecs and how transactions are implemented. Other advantages are pointed out in the FAQ: http://funcool.github.io/clojure.jdbc/latest/#why-another-jdbc-wrapper

peterdee22:10:37

I'm not having much luck trying to write a pmap-like function that times-out after a specified number of milliseconds. I tried two implementations: one with futures and one with core.async. The more complicated futures one passes tests but doesn't stop processes when running in my project. The core.async one is even worse in that regard. I'm new to core.async. If you care to take a look, the code is here: https://github.com/pdenno/utils4pmap/blob/master/src/pdenno/utils4pmap.clj There are tests in utils4pmap_test.clj

noisesmith06:10:43

future-cancel is unreliable, if you want something to be cancellable you need to ensure it regularly calls some cancellable method (the list is relatively short) https://docs.oracle.com/javase/7/docs/api/java/util/concurrent/Future.html#cancel(boolean)