Clojure clj-time : parse local string - clojure

I have trouble making the interop between java.util.Date and clj-time.
I have first raw data which is an instance of java.util.Date, let's day :
(def date (new java.util.util.Date))
I want to turn in into a clj-time object so I do :
(def st-date (.toString date))
Output :
"Mon Mar 21 16:39:23 CET 2016"
I define a formatter
(def date-formatter (tif/formatter "EEE MMM dd HH:mm:ss zzz yyyy"))
All is here I think.
I so try
(tif/parse order-date-formatter st-date)
I have an exception which tell me the format is not right.
I tried
(tif/unparse order-date-formatter (tic/now))
And I have
"lun. mars 21 15:50:29 UTC 2016"
Which is the same datetime as the java String but in French (my language) with UTC
Wrapping the code for test
(defn today-date-to-clj []
(let [st-date (.toString (new java.util.util.Date))
date-formatter (tif/formatter "EEE MMM dd HH:mm:ss zzz yyyy")]
(tif/parse date-formatter st-date)))
I seems that the formatter does not work on the string because it's not the same localization, am I right ? How to change it ?
Thanks for the help !
EDIT
Someone gave me a far better answer but this almost worked for curious people (problem at "CET 2016" but works for unparse)
(def uni-formatter (tif/with-locale (tif/with-zone order-date-formatter (DateTimeZone/forID "Europe/Paris")) java.util.Locale/US))

Instead of using String as an intermediate date representation you should use a direct conversion:
(clj-time.coerce/from-date (java.util.Date.))

Take a closer look at clj-time's coerce functions.
You can pass your java.util.Date object to from-date or from-date-time to get a org.joda.time.DateTime and then apply it to your custom formatter:
(require '[clj-time
[coerce :as c]
[format :as f]])
(->> (java.util.Date.)
(c/to-date-time)
(f/unparse date-formatter))

Related

How to reformat this datetime without regex in Google Sheets?

In Google Sheets i want to reformat this datetime Mon, 08 Mar 2021 10:57:15 GMT into this 08/03/2021.
Using RegEx i achieve the goal with
=to_date(datevalue(REGEXEXTRACT("Mon, 08 Mar 2021 10:57:15 GMT","\b[0-9]{2}\s\D{3}\s[0-9]{4}\b")))
But how can i do it without RegEx? This datetime format seems to be a classic one - can it really be, that no onboard formula can't do it? I rather think, i miss the right knowledge here...
Please try the following formula and format as date
=TRIM(LEFT(INDEX(SPLIT(K13,","),,2),12))*1
(do adjust according to your locale)
Another option is to use Custom Script.
Example:
Code:
function formatDate(date) {
return Utilities.formatDate(new Date(date), "GMT", "dd/MM/YYYY")
}
Formula in B1: =formatDate(A1)
Output:
Reference:
Custom Functions in Google Sheets

Clojure - group by two values, count on specific key word

I have an xml file which I have read in and indexed on my editor. I have three status' by which they are denoted in the xml file - GOOD, AVERAGE, POOR; and they are also indexed by a date in DD/MM/YYYY format.
What I have to do is group them initially by month, so therefore stripping the month out of the date which I have successfully done and then loop through again and count the 'GOOD' status' on a per month basis.
I would assume that I would have to group by both Month and Status and then count the occurances of 'GOOD' although I seem to be getting stuck somewhere... what I have developed so far is below, hopefully I just need to tweak it slightly!
...data fed in from xml...
data (doall (get-records (xml/parse is)))
loopA (for [flop data]
{
:STATUS(:QUALITY_STATUS flop)
:MONTH(get (split (:DATE flop) #"/") 1)
})
x(group-by #(select-keys %[:MONTH :STATUS]) loopA)
loopB (str-join \newline (for [floop x]
{
:MONTH_STAMP (second floop)
:Q_STATUS (if (= :STATUS "GOOD") (second floop))
:GOOD_QUAL (count :Q_STATUS)
}))
Ideally what i want to end up with is three columns of data like the below:
Month -- Quality -- Count
01 ------- GOOD ----- 1
02 ------- GOOD ----- 5
...
12 ------- GOOD ----- 3
Thanks in advance! :)

Supplying a default value for left outer joins

I was wondering what would be the best way of specifying a default value when doing an outer-join in cascalog for field that could be null.
(def example-query
(<- [?id ?fname ?lname !days-active]
(users :> ?id ?fname ?lname)
(active :> ?fname ?lname !days-active))
In this example users and active would be previously defined queries and I'm just looking to correlate active user information (?fname ?lname !days-active) and regular user information (?id ?fname ?lname)
So when the join happened if there was no corresponding information for !days-active it would output 0 instead of nil
i.e.
392393 john smith 3
003030 jane doe 0
instead of
392393 john smith 3
003030 jane doe null
Updated Example
(<- [!!database-id ?feature !!user-clicks !!engaged-users ?application-id ?active-users]
(app-id-db-id-feature-clicks-engaged :> ?application-id !!database-id ?feature !!user-clicks !!engaged-users )
(user-info :> ?application-id ?feature ?active-users))]
example output would look something roughly like
4234 search null null 222 5000
3232 profile 500 400 331 6000
with the filtering that I'm interested I could change the fields that would be !!engaged-users and !!user-clicks to have 0 instead of null. Would using multiple Or predicates work?
I think what you want to do is add an or predicate:
(def example-query
(<- [?id ?fname ?lname !days-active]
(users :> ?id ?fname ?lname)
(active :> ?fname ?lname !days-active)
(or !days-active 0 :> ?active-days)))
That's not an outer join, by the way, it's just not filtering out null variables in the !days-active position.

how to get add a custom-parser in clj-time for AM / PM

I am using clj-time for processing dates. I have a date (def a (date-time 2011 01 01 11 30)).
I have defined a custom formatter (def custom-formatter (formatter "hh:mm"))
Now (unparse custom-formatter a) => "11:30".
However how do I build a formatter which gives me the AM and PM also respectively?
Thanks,
Murtaza
See http://joda-time.sourceforge.net/apidocs/org/joda/time/format/DateTimeFormat.html
To get what you want you need to use something like the following pattern:
(formatter "h:mm a")

Why doesn't model-query return query results? (clj-plaza)

I am using clj-plaza (0.0.5-SNAPSHOT) to query a Sesame/Jena Model. The function model-query does not appear to execute the query. It returns the internal representation of a clj-plaza query instead.
(init-jena-framework)
(def *m* (build-model))
(with-model *m*
(model-add-triples
(model-to-triples
(document-to-model "http://www.rdfdata.org/dat/rdfdata.rdf"
:rdf))))
(def all-subjects-query
(defquery
(query-set-vars [:?subject])
(query-set-pattern (make-pattern [[:?subject ?p ?o]]))
(query-set-type :select))
;; As expected
(model-query-triples *m* all-subjects-query)
=> clojure.lang.LazySeq#2e1e8502
;; Does not execute query (?)
(model-query *m* all-subjects-query)
=> {:kind :select, :pattern [[:?object :?p :?o]], :vars [:?object]}
The official tutorial claims model-query returns a list of bindings from the query:
({:?object "http://randomurl.com/asdf"}
{:?object "http://asdf.com/qwer"})
This is a bug.
Here is a fix. Until it is merged back and updated on clojars, feel free to use my fork.
A workaround would be to use (query model query) (instead of model-query)after importing the corresponding Jena or Sesame implementation.
For Sesame:
(use 'plaza.rdf.implementations.sesame)
(init-sesame-framework)
(def *m* (build-model))
(with-model *m*
(model-add-triples
(model-to-triples
(document-to-model "http://www.rdfdata.org/dat/rdfdata.rdf"
:rdf))))
(def all-subjects-query
(defquery
(query-set-vars [:?subject])
(query-set-pattern (make-pattern [[:?subject ?p ?o]]))
(query-set-type :select))
(query *m* all-subjects-query)
=> [{:?s #<SesameResource http://www.rdfdata.org/dat/rdfdata.rdf>}
{:?s #<SesameResource http://www.rdfdata.org/dat/rdfdata.rdf>}
{:?s #<SesameResource http://www.rdfdata.org/dat/rdfdata.rdf>}
{:?s #<SesameResource http://www.rdfdata.org/dat/rdfdata.rdf>}
{:?s #<SesameResource http://rdfweb.org/topic/FOAFBulletinBoard>}
{:?s #<SesameResource http://rdfweb.org/topic/FOAFBulletinBoard>} ...