Fork me on GitHub
#beginners
<
2018-11-17
>
anantpaatra05:11:31

I need to build a function that takes a string and a number, compares the amount of characters of both and, if the string is shorter than the number, attach more of the same string to the end of the first one until it gets the size of the number. So if I enter the string test and the number 8 it would return testtest. So far the way I tried to do it is to loop, checking if the string is equal or greater in number of characters to the number, and then applying something like (subs string 0 number) to the result, but things aren't working as I expected, and it looks really ugly, I'm for more than an hour trying to spot what's going wrong. Any ideas on how to accomplish this in a different way?

anantpaatra05:11:38

Ok, got it working:

(defn make-secret [text length]
  (loop [secret text]
    (if (< (count secret) length)
      (recur (str secret secret))
      (subs secret 0 length))))
But would still like feedback if I could improve something. Thanks.

jaihindh.reddy08:11:03

@anantpaatra although strings aren't sequences themselves (`(seq? "test")`) they are seqable (`(seqable? "test")`) which means you can call seq to get a sequence of characters of the string. And this means that you can use all of Clojure's sequence functions on strings directly. Here's what I came up with

(defn make-secret [text len]
  (->> (cycle text)
       (take len)
       (apply str)))

anantpaatra20:11:56

This is just awesome and so elegant. Thanks 😄

jaihindh.reddy20:11:03

Peruse when you have time. Lots of useful sequence functions in the core library. Many of them are have multiple arities that make sense. partition for example, can also overlap the partitions. Clojure is elegant 😄

joebetz9111:11:46

how do I evaluate a list of zero argument lambdas?

schmee12:11:15

(map #(%) fns)

joebetz9113:11:20

thanks. is there a better way to do this? I've got the html now, but the components in the list are rerendering more often than they should be, and I suspect it's because of how they're evaluated.

joebetz9113:11:46

right now I've got: (doall (map #(%) (map (partial note-view) notes))))

joebetz9114:11:30

okay, I fixed it. turns out the issue was that I was calling note-view with square brackets rather than round. I switched it to (doall (for [note notes] [note-view note])) and now it's working.

jaihindh.reddy16:11:15

@ you aren't calling note-view here too. How's it working?

joebetz9117:11:46

afaik, it's something unique to reagent, and is how it figures out what to render as react components

joebetz9117:11:29

but yeah, it's weird, and I don't like it

joebetz9111:11:04

context: I'm adding local state to a re-frame render function, so I want a list of hiccup / html data, but instead I'm getting a list of zero argument functions

joebetz9111:11:45

(doall (map (partial note-view) notes))

(defn note-view
  [note]
  (let [local-state (reagent/atom "")]
    (fn [] [:div ... ])))

jaihindh.reddy19:11:23

I tend to eval (use 'clojure.repl), (use 'clojure.pprint) and (require '[clojure.spec.alpha :as s]) every time I open my REPL with rebel-readline. Can I automate this somehow?

vheuken21:11:10

Does anyone know how to upgrade the clojure version used by lein repl when used outside of a project directory? I tried adding the following to ~/.lein/profiles.clj but it had no effect:

{:profiles
 {:repl {:dependencies [^:displace [org.clojure/clojure "1.10.0-beta5"]]}}}

vheuken21:11:45

lein repl is clearly reading the file just fine, since it gives me an error/warning if i have a typo in the file

jesse.wertheim21:11:11

@vheuken well you don't need the outer {:profiles } map in ~/.lein/profiles.clj, you can just do {:repl {... } } but strangely I just checked and mine doesn't seem to be respecting it either, though it does respect the plugins I have in my user profile

vheuken21:11:41

Yeah, I tried it wwithout the outer {profiles map originally.

vheuken21:11:44

Not sure what's going on

vheuken21:11:52

I took it straight out of the lein docs

jesse.wertheim21:11:03

oddly I changed my test to beta4 and it DID download beta4, it just didn't use it to launch the repl

vheuken21:11:30

Perhaps a bug in lein i should report?

seancorfield21:11:02

By the time Leiningen reads that file, it's already loaded Clojure so you can't change it.

jesse.wertheim21:11:35

still a bug in that case, then, since it's documented

seancorfield21:11:49

Oh, interesting. You never used to be able to do that I think...

seancorfield21:11:09

Weird, it downloads the specified version, but still doesn't use it. Probably a regression from some version where it used to work?

jesse.wertheim21:11:21

that would be my guess

jesse.wertheim21:11:44

in the meantime there's always the clojure cli tools! what I did was set up a beta alias for 1.10.0-beta5 so I can launch a beta repl with clj -A:beta outside of a project

seancorfield22:11:13

Yup, it works in 2.7.1

seancorfield22:11:59

[email protected]:~/clojure$ lein upgrade 2.7.1
The script at /home/seanc/bin/lein will be upgraded to the latest 2.7.1 version.
Do you want to continue [Y/n]?

Upgrading......
Leiningen 2.7.1 on Java 1.8.0_181 OpenJDK 64-Bit Server VM
[email protected]:~/clojure$ lein repl
nREPL server started on port 56061 on host 127.0.0.1 - 
REPL-y 0.3.7, nREPL 0.2.12
Clojure 1.10.0-beta6
OpenJDK 64-Bit Server VM 1.8.0_181-8u181-b13-0ubuntu0.16.04.1-b13
...
user=>

seancorfield22:11:13

(you can use lein upgrade to go up and down the releases)

vheuken22:11:48

I'll look into clojure cli tools. Thanks!

seancorfield22:11:04

We do everything with the CLI tools at work. We started on Leiningen back in 2011, switched to Boot at the end of 2015, and just switched over to clojure and deps.edn in the last month or so.

vheuken22:11:57

Neat. I've been meaning to give that kind of workflow a try anyway. Always had trouble maintaining a clean lein config...

jesse.wertheim22:11:47

the only thing I miss with the CLI tools so far is being able to just define tasks as code without having to throw a scripts dir somewhere. well that and lein and boot do provide some plugins/tasks that take away some of the manual tinkering you have to do with a few common setups

jesse.wertheim22:11:13

granted I've only done light work with boot anyway and I'm still relatively new to everything

vheuken22:11:25

I prefer a scripts dir, honestly.

jesse.wertheim22:11:57

I'd be cool with it if I could refer to env vars from deps.edn

jesse.wertheim22:11:10

(unless you can and I just can't find how)

seancorfield22:11:22

Boot's ability to let you define arbitrary tasks in your build.boot is a double-edged sword. We ended up with 2,000 lines of code in ours over the years 🙂 Breaking things into separate scripts is good practice -- that CLI forces on you.

jesse.wertheim22:11:35

yeah that's fair

seancorfield22:11:10

deps.edn is pure data -- no way to have env vars in it. What would you want to use env vars for? (so maybe there's a way to achieve it)

jesse.wertheim22:11:38

mainly just to clean up how local deps are handled. Like, the other day I wrote a tiny script that sets up rebel-readline and also spins up a cider-nrepl server, since there isn't currently a built-in integration, and it'd be nice to not have to hard-code a fixed path into my home directory. Not a huge deal - I should probably throw it in a git repo or something anyway

jesse.wertheim22:11:35

couldn't it be done via a tag? env vars in deps.edn, I mean

jesse.wertheim22:11:12

eh I suppose I can see why it wouldnt' be considered a good practice, regardless

jesse.wertheim22:11:01

@seancorfield the main env var of interest are the ones used by clj itself - $HOME, $CLJ_CONFIG, and $XDG_CONFIG_HOME - for instances where you might want to configure some general tooling that doesn't live in any one project

jesse.wertheim22:11:48

what might be better is a way to resolve relative paths but that almost seems like a taller order given the JVM of it all

jesse.wertheim22:11:32

hmm you know it should be pretty easy to write up some kinda dispatcher script for such things, and just use that - but more likely I'll just throw my custom central stuff into a git URL so I don't have to worry about hardcoding a local absolute path for it. it doesn't come up THAT often

seancorfield22:11:29

We have a monorepo with a lot of subprojects. One subproject is special and provides all the pinned versions (in a :defaults alias with :override-deps for everything).

seancorfield22:11:01

So then we do CLJ_CONFIG=../versions clojure -A:defaults:other:aliases in each one as needed.

jesse.wertheim22:11:34

one decision I love about clojure CLI tools is the fact that you can define one or more clojure version right from there - putting the version manager in the official tooling. almost every other language I can think of requires a userland solution for version management

seancorfield22:11:47

And we have a simple build shell script to automate that part, so build alias:list subproject does a cd to that subproject and then runs the clojure command.

jesse.wertheim22:11:58

yeah that makes sense!

seancorfield22:11:29

We have a build subproject which has various short scripts with -main functions that can be invoked via aliases. We also have a dev subproject with REPL-starting code that can be pulled in as a :local/root dependency, as I recall.

veix.q522:11:06

is defrecord non-variadic?

seancorfield22:11:24

@jesse.wertheim Like this

:nrepl ; modern nREPL server
  {:extra-deps {ws/dev {:local/root "../dev"}
                nrepl {:mvn/version "RELEASE"}}
   :main-opts ["-m" "ws.dev.nrepl"]}

seancorfield22:11:58

(and you can specify a port for the REPL as a command-line argument)

seancorfield22:11:23

@veix.q5 defrecord takes a fixed list of fields that the record will contain.

jesse.wertheim22:11:51

@seancorfield thanks this is giving my some ideas for a good local setup. I'm also looking to do something for the kinds of tooling you may want as an individual without polluting a project

jesse.wertheim22:11:55

@seancorfield I was under the mistaken impression that it doesn't like relative paths, but it's because I was trying it as a script without making it into a full dep folder with a src dir and its own deps.edn - and running it via main-opts, where of course the relative path wouldn't work

seancorfield22:11:57

Yeah, we have to have all the subprojects at the same "level" (inside a clojure top-level folder in our repo) so that the relative paths all work -- because tools.deps doesn't currently deal with transitive relative paths very well (they all end up relative to where you start the script, instead of being relative to their respective deps.edn files).

jesse.wertheim22:11:32

yep - tested that out a minute ago by setting the relative path with regard to my home folder and then launching the alias from there

jswaney23:11:44

Hi all, I do a lot of 3D image processing in python and I was wondering what tools are out there in the Clojure ecosystem. One nice thing about python is that so many libraries agree on using numpy ndarrays, but idk if there's such a standard in Clojure (core.matrix?). I eventually want to shift to Clojure to make parallel image processing easier, maybe even distributed with something like Onyx.