I want to get a list of all instants between today and (today - 15) days.
I am understanding I might need to you use LazyList if scala, but I am not so familiar with the syntax since I am new. The java equivalent seems to be
Set <Instant> allPossibleDates =
Stream.iterate(today, date -> date.minus(1, ChronoUnit.DAYS))
.limit(numDates)
.collect(Collectors.toSet());
What is the equivalent for this in Scala?
The LazyList companion object defines an iterate method that lets you define a sequence in terms of a starting point and a step operation (Note: Iterator's companion defines a similar method):
def iterate[A](start: => A)(f: (A) => A): LazyList[A]
In fact it looks essentially the same as the Java version except that the start and f arguments appear in separate parameter lists. Pepper in Scala's syntax sugar for anonymous functions (using _ to represent the function argument), you can do
val today = Instant.now() // or whatever
LazyList
.iterate(today) { _.minus(1, ChronoUnit.DAYS) }
.take(15) // equivalent to `limit` in Java
.to(Set) // equivalent to `collect(...)`
Also note that LazyList defines an overload of iterate which takes a limit, which would replace the .take:
LazyList
.iterate(today, 15) { _.minus(1, ChronoUnit.DAYS) }
.to(Set)
Note that you could do .foreach { instant => /* ... */ } instead of .to(SomeCollectionCompanion) to iterate the contents without allocating the memory for a collection.
Related
I am having an issue where I believe I have to combine several concepts that I am reading about, but I can't seem to figure out a way to combine them that makes sense, or what would be most efficient. Here is my situation:
I am working with microservices which is why this is so oddly specific. Essentially I am getting a list of Volume objects from another service. A volume object contains three fields, a String type, a String date(which actually represents time in the format "HH:mm", blame the data modelers for the naming conventions), and an int close.
What I am trying to do is to take this list of objects and sort by date(time), then create a new list of objects which will contain the same dates(times), but will have different field values based off of calculations I am doing. In order to sort by time, I believe I need to convert the time fields to Date objects and then compare those. I'm struggling how to iterate through the objects and compare the converted fields. Something that I feel like has put me on the right path is this: How to sort a List<Object> alphabetically using Object name field
But I can't seem to get that to work. Here's my code:
volumeResources.sort(volumeResources, new Comparator<VolumeResource>(){
#Override
public int compare(VolumeResource v1, VolumeResource v2) {
SimpleDateFormat format = new SimpleDateFormat("HH:mm");
try {
Date d1 = format.parse(v1.getDate());
Date d2 = format.parse(v2.getDate());
} catch (ParseException e) {
log.error("Error in parsing string to date. ", e);
}
return d1.compareTo(d2);
}
});
Now right off the bat, I know that this must be incorrect because I started comparing the VolumeResources v1 and v2, but instead tried to compare the dates at the end. In place of the return statement above, I have also tried the one below, but I don't think that will always work because it's not actually setting the formatted object to a Date object:
return format.parse(v1.getDate()).compareTo(format.parse(v2.getDate()));
So that's where I'm lost. This seems like a fairly simple need when described in pseudocode, but I can't seem to figure out how to make it work functionally. Bonus points if there's a way I can populate the other fields I need easily from this. Double bonus points for using lambdas or helping me make this efficient.
Thanks for any and all help everyone.
If you are using Java 8 and above the sorting by time (which is represented as String) may look like this:
volumeResources.sort(new Comparator<VolumeResource>() {
#Override
public int compare(VolumeResource v1, VolumeResource v2) {
return v1.getDate().compareTo(v2.getDate());
}
});
Prior Java 8 it should look like:
Collections.sort(volumeResources, new Comparator<VolumeResource>() {
#Override
public int compare(VolumeResource v1, VolumeResource v2) {
return v1.getDate().compareTo(v2.getDate());
}
});
Using lambda:
volumeResources.sort((v1, v2) -> v1.getDate().compareTo(v2.getDate()));
Assuming that volumeResources is a populated mutable List (not null) and all entries have date field populated properly with a well formed time (no spaces, tabs, or missing leading 0)
Explanation
According to your definition of date field it is naturally sortable as a string, you do not need to convert them into java Date class.
Your example has an issue by using Java 8 sort method defined in List interface in a manner how it used to be prior Java 8 by using utility class Collections - this is wrong, you do not need to supply collection as a first parameter.
A date in Java must have year, month, day.
But you don't have such values, you have only HH:mm (hours, minutes).
Using dates is not appropriate here.
(And calling these values "date" is also strange, I suggest to rename.)
Notice that well-formed HH:mm can be sorted alphabetically to order correctly. So all you need to do is ensure that the input times follow \d\d:\d\d pattern. If you get for example 9:15 then add a padding 0 at the left. Something like this:
volumeResources.sort(volumeResources, new Comparator<VolumeResource>() {
#Override
public int compare(VolumeResource v1, VolumeResource v2) {
return sanitized(v1.getDate()).compareTo(sanitized(v2.getDate());
}
});
The sanitized method is for you to implement accordingly.
If the values are already in the correct format, of type String, then you can drop these calls and simplify to:
return v1.getDate().compareTo(v2.getDate();
Using lambda:
volumeResources.sort(volumeResources, (v1, v2) -> sanitized(v1.getDate()).compareTo(sanitized(v2.getDate()));
I am going to call the .toUpperCase method within a doto macro like follows but the doto returns the small letters:
(doto (java.lang.String. "clojure")
(.toUpperCase))
returns "clojure". I do the macroexpansion and as the return value is the object created:
(clojure.core/let [G__7359 (java.lang.String. "cojure")] (.toUpperCase G__7359) G__7359)
, but why i don't get the uppercased answer?
doto is part of Clojure's Java interop features. It is designed to make it possible to write java with out soooo darn many parens. so
Foo foo = new Foo;
foo.setX().setY().makeFactory().applyPhaseOfMoon();
which has 8 parens becomes:
(doto foo .setY .makeFactory .applyPhaseOfMoon)
which has a total of two.
In this case if we dig into the expanstion of your example:
user> (doto "hi" .toUpperCase)
"hi"
expands to:
user> (macroexpand-1 '(doto "hi" .toUpperCase))
(clojure.core/let [G__110453 "hi"]
(.toUpperCase G__110453)
G__110453)
where the second line does this:
user> (.toUpperCase "hi")
"HI"
and then throws the answer away and returns the saved value form the start. I personally never see doto used in practice outside of places where people are translating java to clojure inorder to call some API.
From the documentation:
Evaluates x then calls all of the methods and functions with the value
of x supplied at the front of the given arguments. The forms are
evaluated in order. Returns x.
doto returns the original argument, not any the result of functions performed using it. I believe the doto function is generally intended for side-effects. This is why you get the original string back.
What you are looking for is the .. threading macro ( https://clojuredocs.org/clojure.core/_.. ):
Expands into a member access (.) of the first member on the first
argument, followed by the next member on the result, etc. For
instance:
(.. System (getProperties) (get "os.name"))
expands to:
(. (. System (getProperties)) (get "os.name"))
but is easier to write, read, and understand.
In your case:
(doto "clojure" .toUpperCase)
; => "clojure"
(.. "clojure" toUpperCase)
; => "CLOJURE"
While working through converting some Java code over to Scala, I discovered while there is a contains method for Scala's Set, there isn't a containsAll method. Am I just missing the correct method name?
Here's a bit of code I worked up to fill in the gap so I could quickly get back to working. Is it sufficient, or am I missing some subtlety?
def containsAll[A](set: Set[A], subset: Set[A]): Boolean =
if (set.size >= subset.size)
subset.forall(a => set.contains(a))
else
false
There is subsetOf, which tests whether or not the elements of a Set are contained within another Set. (Kind of the reverse in terms of the expression)
val set = Set(1,2,3,4)
val subset = Set(1,2)
scala> subset.subsetOf(set)
res0: Boolean = true
scala> set.subsetOf(subset)
res1: Boolean = false
In Scala, Set is equipped with set operations such as intersect, thus for instance
set.intersect(subset) == subset
conveys the semantics of containsAll, even that subsetOf as already mentioned proves the most succinct.
It's worth adding that you can make derived helper methods like containsAll available on Set[T] if you want, by using an implicit enriched class. You might also consider making a variadic overload:
implicit class RichSet[T](val x: Set[T]) extends AnyVal {
def containsAll(y: Set[T]): Boolean = y.subsetOf(x)
def containsAll(y: T*): Boolean = x.containsAll(y.toSet)
}
So then you can do:
Set(1, 2, 3).containsAll(Set(1, 2))
Or:
Set(1, 2, 3).containsAll(1, 2)
Previous answers are all good, I'm just throwing-in another option. This one would also work with Lists which don't have subsetOf method:
Set(1,2,3) forall(Set(3, 2, 1) contains)
I'm trying to use Clojure to dynamically generate functions that can be applied to large volumes of data - i.e. a requirement is that the functions be compiled to bytecode in order to execute fast, but their specification is not known until run time.
e.g. suppose I specify functions with a simple DSL like:
(def my-spec [:add [:multiply 2 :param0] 3])
I would like to create a function compile-spec such that:
(compile-spec my-spec)
Would return a compiled function of one parameter x that returns 2x+3.
What is the best way to do this in Clojure?
Hamza Yerlikaya has already made the most important point, which is that Clojure code is always compiled. I'm just adding an illustration and some information on some low-hanging fruit for your optimisation efforts.
Firstly, the above point about Clojure's code always being compiled includes closures returned by higher-order functions and functions created by calling eval on fn / fn* forms and indeed anything else that can act as a Clojure function. Thus you don't need a separate DSL to describe functions, just use higher order functions (and possibly macros):
(defn make-affine-function [a b]
(fn [x] (+ (* a x) b)))
((make-affine-function 31 47) 5)
; => 202
Things would be more interesting if your specs were to include information about the types of parameters, as then you could be interested in writing a macro to generate code using those type hints. The simplest example I can think of would be a variant of the above:
(defmacro make-primitive-affine-function [t a b]
(let [cast #(list (symbol (name t)) %)
x (gensym "x")]
`(fn [~x] (+ (* ~(cast a) ~(cast x)) ~(cast b)))))
((make-primitive-affine-function :int 31 47) 5)
; => 202
Use :int, :long, :float or :double (or the non-namespace-qualified symbols of corresponding names) as the first argument to take advantage of unboxed primitive arithmetic appropriate for your argument types. Depending on what your function's doing, this may give you a very significant performance boost.
Other types of hints are normally provided with the #^Foo bar syntax (^Foo bar does the same thing in 1.2); if you want to add them to macro-generated code, investigate the with-meta function (you'll need to merge '{:tag Foo} into the metadata of the symbols representing the formal arguments to your functions or let-introduced locals that you wish to put type hints on).
Oh, and in case you'd still like to know how to implement your original idea...
You can always construct the Clojure expression to define your function -- (list 'fn ['x] (a-magic-function-to-generate-some-code some-args ...)) -- and call eval on the result. That would enable you to do something like the following (it would be simpler to require that the spec includes the parameter list, but here's a version assuming arguments are to be fished out from the spec, are all called paramFOO and are to be lexicographically sorted):
(require '[clojure.walk :as walk])
(defn compile-spec [spec]
(let [params (atom #{})]
(walk/prewalk
(fn [item]
(if (and (symbol? item) (.startsWith (name item) "param"))
(do (swap! params conj item)
item)
item))
spec)
(eval `(fn [~#(sort #params)] ~#spec))))
(def my-spec '[(+ (* 31 param0) 47)])
((compile-spec my-spec) 5)
; => 202
The vast majority of the time, there is no good reason to do things this way and it should be avoided; use higher-order functions and macros instead. However, if you're doing something like, say, evolutionary programming, then it's there, providing the ultimate flexibility -- and the result is still a compiled function.
Even if you don't AOT compile your code, as soon as you define a function it gets compiled to bytecode on the fly.
I need something like this, a collection of elements which contains no duplicates of any element. Does Common Lisp, specifically SBCL, have any thing like this?
For a quick solution, just use hash tables, as has been mentioned before.
However, if you prefer a more principled approach, you can take a look at FSet, which is “a functional set-theoretic collections library”. Among others, it contains classes and operations for sets and bags.
(EDIT:) The cleanest way would probably be to define your set-oriented operations as generic functions. A set of generic functions is basically equivalent to a Java interface, after all. You can simply implement methods on the standard HASH-TABLE class as a first prototype and allow other implementations as well.
Look at cl-containers. There is a set-container class.
You could use lists, though they can prove to be inefficient for representing large sets. This is done using ADJOIN or PUSHNEW to add a new element to a list, and DELETE or REMOVE to do the opposite.
(let ((set (list)))
(pushnew 11 set)
(pushnew 42 set)
(pushnew 11 set)
(print set) ; set={42,11}
(setq set (delete 42 set))
(print set)) ; set={11}
One thing to watch out for is all that these operators use EQL by default to test for potential duplicates in the set (much as Java uses the equals method). That's OK for sets holding numbers or characters, but for sets of other objects, a `deeper' equality test such as EQUAL should be specified as a :TEST keyword parameter, e.g. for a set of strings :-
(let ((set (list)))
(pushnew "foo" set :test #'equal)
(pushnew "bar" set :test #'equal)
(pushnew "foo" set :test #'equal) ; EQUAL decides that "foo"="foo"
(print set)) ; set={"bar","foo"}
Lisp's counterparts to some of Java's Set operations are:
addAll -> UNION or NUNION
containsAll -> SUBSETP
removeAll -> SET-DIFFERENCE or NSET-DIFFERENCE
retainAll -> INTERSECTION or NINTERSECTION
Yes, it has sets. See this section on "Sets" from Practical Common Lisp.
Basically, you can create a set with pushnew and adjoin, query it with member, member-if and member-if-not, and combine it with other sets with functions like intersection, union, set-difference, set-exclusive-or and subsetp.
Easily solvable using a hash table.
(let ((h (make-hash-table :test 'equalp))) ; if you're storing symbols
(loop for i from 0 upto 20
do (setf (gethash i h) (format nil "Value ~A" i)))
(loop for i from 10 upto 30
do (setf (gethash i h) (format nil "~A eulaV" i)))
(loop for k being the hash-keys of h using (hash-value v)
do (format t "~A => ~A~%" k v)))
outputs
0 => Value 0
1 => Value 1
...
9 => Value 9
10 => 10 eulaV
11 => 11 eulaV
...
29 => 29 eulaV
30 => 30 eulaV
Not that I'm aware of, but you can use hash tables for something quite similar.
Lisp hashtables are CLOS based. Specs here.
Personally, I would just implement a function which takes a list and return a unique set. I've drafted something together which works for me:
(defun make-set (list-in &optional (list-out '()))
(if (endp list-in)
(nreverse list-out)
(make-set
(cdr list-in)
(adjoin (car list-in) list-out :test 'equal))))
Basically, the adjoin function prepends an item to a list non-destructively if and only if the item is not already present in the list, accepting an optional test function (one of the Common Lisp "equal" functions). You can also use pushnew to do so destructively, but I find the tail-recursive implementation to be far more elegant. So, Lisp does export several basic functions that allow you to use a list as a set; no built-in datatype is needed because you can just use different functions for prepending things to a list.
My data source for all of this (not the function, but the info) has been a combination of the Common Lisp HyperSpec and Common Lisp the Language (2nd Edition).