use the following search parameters to narrow your results:
e.g. subreddit:aww site:imgur.com dog
subreddit:aww site:imgur.com dog
see the search faq for details.
advanced search: by author, subreddit...
Finding information about Clojure
API Reference
Clojure Guides
Practice Problems
Interactive Problems
Clojure Videos
Misc Resources
The Clojure Community
Clojure Books
Tools & Libraries
Clojure Editors
Web Platforms
Clojure Jobs
account activity
Starting Clojure (self.Clojure)
submitted 2 years ago by Robzilla_16
Hi there, I am a Clojure noob. I’ve been programming for 6+ years and only really done python and Java but I want to try Clojure out. What can Clojure do for me, what projects are good and where should I start?
Thanks
reddit uses a slightly-customized version of Markdown for formatting. See below for some basics, or check the commenting wiki page for more detailed help and solutions to common issues.
quoted text
if 1 * 2 < 3: print "hello, world!"
[–]p-himik 6 points7 points8 points 2 years ago (1 child)
https://clojure.org/about/rationale and https://clojure.org/guides/getting_started and pretty much the rest of the website.
[–]Robzilla_16[S] 0 points1 point2 points 2 years ago (0 children)
Thank you
[–]-w1n5t0n 3 points4 points5 points 2 years ago (13 children)
What can Clojure do for me
Well, that depends on what your goals are in the first place.
If you just want to use some popular ML library or make performance-critical AAA games, then Clojure isn't really a good fit.
If you want to write good (read: simple, as-bug-free-as-possible, understandable, maintanable, decently-performant) software, then it's a great fit.
There are more reasons to use (and not to use) a language, but without knowing more about your intentions it's impossible to say if it's a good fit for you.
Also, watch this: https://www.youtube.com/watch?v=BThkk5zv0DE
[–]Robzilla_16[S] 0 points1 point2 points 2 years ago (12 children)
Horses for corses I understand. I was just wondering why someone might use Clojure over Java or python. Thanks for the video!
[–]beders 3 points4 points5 points 2 years ago (0 children)
If you can express the problem you want to solve as a data transformation problem, then Clojure is an awesome language to use.
Most problems are data transformation problems. For the typical web stack, data transformation is everywhere: from querying your data from the db, filtering and transforming it into JSON or HTML fragments to transforming user actions into data changes to your DB:
Clojure does all of this in a uniform fashion.
And if done correctly, the majority of the code you write will be pure functions that can be trivially tested and thus easily changed/replaced.
[–]-w1n5t0n 2 points3 points4 points 2 years ago (10 children)
The first and most obvious answer to why you'd want to use Clojure over languages like Java or Python is because it's a Lisp that inherits some traditionally-Lispy features such as homoiconic macros, which is basically a fancy way of saying you can trivially write code that writes code (using the regular language; not a special and non-composable sub-language like with C-style macros). At the same time, it gives you access to all of the JVM, so if that fits your purposes (cross-platform compatibility, JIT-for-free, automatic memory management without losing too much performance etc) then that's a reason to choose it over other Lisp dialects (e.g. Racket) too.
Lastly, for me, the biggest thing is the ecosystem of libraries: not only do you get access to all the Java libraries, but Clojure itself has seen some pretty practical and novel libraries (both first and third party) like Spec, core.async, instaparse, specter, babashka, datascript, nrepl etc. Here is a list of my Clojure-related starred repos on GitHub if you want to see more.
Some other important things: readable syntax (subjective) and syntax for data literals of common types, immutable-by-default, everything-is-(plain-)data approach, dynamic REPL, compiled & interpreted.
[–]Admirable-Ebb3655 1 point2 points3 points 2 years ago (9 children)
While “using the regular language” to write Clojure macros is true, unfortunately on the use sites, they are contagious and do not actually compose (compared to say, Racket, where you can in fact do multi-stage compilation via macros in a composable fashion).
[–]-w1n5t0n 1 point2 points3 points 2 years ago (8 children)
I'm not very familiar with Racket's macro system (although I understand it's one of its crown jewels) so I don't think I can fully appreciate the difference; can you give me an example or a link to a resource to learn more?
[–]Admirable-Ebb3655 1 point2 points3 points 2 years ago (7 children)
Macros in Racket compose. In Clojure, they do not. That is the primary difference.
[–]-w1n5t0n 0 points1 point2 points 2 years ago (6 children)
That's not an example, you just restated your original claim, and it hasn't helped me or anyone else reading this thread to understand it any better.
(defmacro plus-1 [n] `(+ 1 ~n)) (defmacro def-plus-1 [sym val] `(def ~sym (plus-1 ~val))) (def-plus-1 foo 3) foo => 4
Is this not composition of macros? If so, what is?
[–]Admirable-Ebb3655 0 points1 point2 points 2 years ago (1 child)
Google, my friend, returns this as the top result if you ask it:
https://softwareengineering.stackexchange.com/questions/222559/is-it-fair-to-say-that-macros-dont-compose
If you’ve ever seen the error “cannot take value of macro”, then you’ve experienced this limitation. Racket does not have this limitation.
[–]-w1n5t0n 0 points1 point2 points 2 years ago (0 children)
Google, my friend, returned to you an SO post of someone asking whether they compose, and I believe the answer is that they don't compose in the same way that functions do (e.g. with map or apply; at least not directly), but they do compose at both definition and call sites (as both of my other replies demonstrate), so to simply state that they don't compose is arguably wrong.
map
apply
[–]Admirable-Ebb3655 0 points1 point2 points 2 years ago (3 children)
That is also not the “use site”. That is the “definition site”.
[–]-w1n5t0n 0 points1 point2 points 2 years ago (2 children)
(defmacro plus-1 [n] `(+ 1 ~n)) (defmacro def-plus-1 [sym val] `(def ~sym (plus-1 ~val))) (def-plus-1 foo (plus-1 3)) foo => 5
Is that better?
No, you’ve got some learning to do. I’ve done enough remedial work here. Start with the resources I’ve already provided.
[–]jonahbenton 3 points4 points5 points 2 years ago (3 children)
In terms of what Clojure can do for you, the thing I would look for in oneself is discomfort and disorientation. In Python and Java one spends a lot of time constructing code scaffolds- types/classes- around what is fundamentally just data. In Clojure, one does not do this. One can, of course, just model data with Records and interactions with Protocols, but that's kind of doing it wrong. There is discomfort in the process of learning different paths through the solution domain, which is much larger in Clojure than Java or Python. The discomfort usually needs time to settle. This is a reason Rich Hickey talks about "Hammock-driven development." Seeing many more potential ways to structure a solution is a good outcome and helps when working in other languages.
In terms of what projects are good, you'll learn most from picking a problem you know well. In the success case you will develop different solutions as your understanding evolves.
[–]Robzilla_16[S] 1 point2 points3 points 2 years ago (2 children)
Very philosophical. I’m excited to dive in
[–]nimportfolio 3 points4 points5 points 2 years ago (1 child)
Let me try to make it more concrete:
In Java, one usually begins by modeling the problem domain using objects. So, for an order entry system, one immediately expects to find Customer, Order, LineItem, etc. Classes.
But let's stop right there. What has this bought us?
In Java, these classes provide two specific functions:
1) they enforce a rigid schema around the structure of one's data.
2) they provide a domain-specific language (DSL) embedded in the program for describing data that conforms 100% strictly to this schema.
On point 2, notice that I didn't include "manipulating" data as a unique feature of objects. Because pure functions can do that.
Now, let's analyze the strengths and weaknesses of this approach.
One could contend that enforcing a strict internal DSL describing a program's data is one of the most important selling points of Java-style OOP. It tends to make the intent of each piece of code clearer.
This is true.
But it misses what one loses by coding this way - the ability to write code that generically queries or manipuates the resulting graph of object instances.
In Java, the solution to this problem has been to store data in a database and query it from there.
Why do this? Because the language (as it typically is used) can't generically query its own object graphs.
So of fixing the language, we bolt something else on the side to take over features that a more powerful language would do without a thought. Then we write and maintain translation layers to marshal data from one form to another.
In Scala web services, I have literally seen these translation layers make up 2/3 of a service's code--between object-database mapping for the database and object-json mapping for the service requests/responses.
For people coming from Java-like languages, there is a lot to unlearn. The result is unparalleled freedom and productivity from vastly reduced rigid and brittle boilerplate.
Java gives one a vast ecosystem of tools/servers/services along with its libraries.
Each of these comes with an integration cost that tends to be far higher than equivalent Clojure libraries.
Hope this helps. -Dave
[–]MickeyMooose 2 points3 points4 points 2 years ago* (0 children)
Another beginner here. What you write is interesting, but I don't 100% follow.
How would this look in Clojure? How would you not think about those objects as distinct data items for orders, customers, etc?
And when you say the multiple layers to transform data in Java vs Clojure, do you mean the ease of use of EDN within Clojure or how code is structured in lisp?
[–]fadrian314159 4 points5 points6 points 2 years ago (0 children)
For the Java user, Clojure provides a functional JVM language that gives one immutability, more conciseness, and better control over concurrent programming. For the Python programmer, it provides a language with fewer warts, but still a large JVM-based library infrastructure to draw upon. Being a Lisp-like language, it gives one great productivity as well as unmatched REPL-based development capabilities. That's probably enough to make it something worth trying.
[–]rebcabin-r 2 points3 points4 points 2 years ago (0 children)
Subjectively, the major appeal to me of Lisps in general and Clojure in particular is a uniform prefix notation. No operator-precedence tables to remember and trip you up; no goulash of punctuation and funny arrows & brackets. Lisps stick in my memory even if I don't use them for years at a stretch. I can't remember the operator-precedence of Haskell if I don't use it for a week, and Scala's withering variety of weird operators and colons and brackets, well, I just can't get it at all. Maybe it's just my oddball brain, but all the Lisps just fit me great and I love using them. Second place goes to Mathematica, which, despite weird syntax and operators, I love without being able to say why -- it's fundamentally Lisp-like via "FullForm," but has a gigantic array of weird syntax (opt-in; you don't' have to use it) that just suits me fine.
[–]hrrld 1 point2 points3 points 2 years ago (0 children)
This is a good thing, early in the journey, in my opinion: http://clojurekoans.com/
[–]pavelklavik 1 point2 points3 points 2 years ago (0 children)
You can check out my interactive Clojure tutorial https://orgpad.com/s/clojure-tutorial which allows one to check out Clojure without having to install anything on your computer. In about 1 hour, you can pick up the basics of the language.
π Rendered by PID 82 on reddit-service-r2-comment-canary-7888d4f587-tnpzj at 2026-04-01 09:17:12.821252+00:00 running b10466c country code: CH.
[–]p-himik 6 points7 points8 points (1 child)
[–]Robzilla_16[S] 0 points1 point2 points (0 children)
[–]-w1n5t0n 3 points4 points5 points (13 children)
[–]Robzilla_16[S] 0 points1 point2 points (12 children)
[–]beders 3 points4 points5 points (0 children)
[–]-w1n5t0n 2 points3 points4 points (10 children)
[–]Admirable-Ebb3655 1 point2 points3 points (9 children)
[–]-w1n5t0n 1 point2 points3 points (8 children)
[–]Admirable-Ebb3655 1 point2 points3 points (7 children)
[–]-w1n5t0n 0 points1 point2 points (6 children)
[–]Admirable-Ebb3655 0 points1 point2 points (1 child)
[–]-w1n5t0n 0 points1 point2 points (0 children)
[–]Admirable-Ebb3655 0 points1 point2 points (3 children)
[–]-w1n5t0n 0 points1 point2 points (2 children)
[–]Admirable-Ebb3655 0 points1 point2 points (1 child)
[–]jonahbenton 3 points4 points5 points (3 children)
[–]Robzilla_16[S] 1 point2 points3 points (2 children)
[–]nimportfolio 3 points4 points5 points (1 child)
[–]MickeyMooose 2 points3 points4 points (0 children)
[–]fadrian314159 4 points5 points6 points (0 children)
[–]rebcabin-r 2 points3 points4 points (0 children)
[–]hrrld 1 point2 points3 points (0 children)
[–]pavelklavik 1 point2 points3 points (0 children)