In Scala - How to get the day of the week? - scala

Suppose my date format is 21/05/2017 then the output will be SUN.
How can I get the day given a date?

import java.time.LocalDate
import java.time.format.DateTimeFormatter
val df = DateTimeFormatter.ofPattern("dd/MM/yyyy")
val dayOfWeek = LocalDate.parse("21/05/2017",df).getDayOfWeek

You can use SimpleDateFormat as illustrated below:
import java.util.Calendar
import java.text.SimpleDateFormat
val now = Calendar.getInstance.getTime
val date = new SimpleDateFormat("yyyy-MM-dd")
date.format(now)
res1: String = 2017-05-20
val dowInt = new SimpleDateFormat("u")
dowInt.format(now)
res2: String = 6
val dowText = new SimpleDateFormat("E")
dowText.format(now)
res3: String = Sat
[UPDATE]
As per comments below, please note that SimpleDateFormat isn't thread-safe.

You can also use nscala-time which is a Scala wrapper for Java's joda-time which is a datetime library with a ton of functionality.
import com.github.nscala_time.time.Imports._
val someDate =(newDateTime).withYear(2017)
.withMonthOfYear(5)
.withDayOfMonth(21)
someDate.getDayOfWeek
res7: Int = 7
Now you need to know the mapping between integer days of the week and names. Here, 7 corresponds to Sunday.

Related

Get current date as string in databricks using scala

I want to get current date in Scala as a String. For example, today current date is 5th Jan. I want to store it as a new variable dynamically as below.
val currdate : String = “20220105”
When I am using val currdate = Calendar.getInstance.getTime then am not getting output in desired format as above.
This is how it's done using the contemporary java.time library.
import java.time.LocalDate
import java.time.format.DateTimeFormatter
val currdate: String =
LocalDate.now.format(DateTimeFormatter.ofPattern("yyyyMMdd"))
Older utilities like Calendar and SimpleDate still work (mostly) but should be avoided.
Why do you need it as String?
For a Spark query you could use java.sql.Timestamp directly.
This how you get it:
import java.sql.Timestamp
import java.text.SimpleDateFormat
import java.time.Instant
val now: Timestamp =
Timestamp.from(Instant.now())
If you really want a formatted String:
val asString =
new SimpleDateFormat("yyyyMMdd").format(now)
SimpleDateFormat is old and not thread-safe but should do the job.

How to convert the dd/mm/yyyy to yyyymmdd in scala by using joda time

How can I convert the dd/mm/yyyy to yyyymmdd format and also
dd/m/yyyy to yyyymmdd format by using joda time in Scala.
am using this dependency
"joda-time" % "joda-time" % "2.9.9",
This answer already answers your question in Java, but here it is translated into Scala:
import org.joda.time.DateTime
import org.joda.time.format.{DateTimeFormat, DateTimeFormatter}
// define original date format
val originalFormat: DateTimeFormatter = DateTimeFormat.forPattern("dd/MM/yyyy")
val input: DateTime = originalFormat.parseDateTime("02/09/2017")
// define new format
val newFormat: DateTimeFormatter = DateTimeFormat.forPattern("yyyyMMdd")
val output: String = newFormat.print(input) // 20170902
This code will already account for missing a leading 0 from your date (ie it will see 02/9/2017 and 2/9/2017 as the same thing). It will not predict missing parts of the year though, so 2/9/17 will be outputted as 00170902 instead of 20170902.
As the answer I linked to earlier mentions though, you can just use java.time to do the same thing:
import java.time.LocalDate
import java.time.format.DateTimeFormatter
val originalFormat = DateTimeFormatter.ofPattern("dd/MM/yyyy")
val input = LocalDate.parse("02/09/2017", originalFormat)
val newFormat = DateTimeFormatter.ofPattern("yyyyMMdd")
val output = input.format(newFormat)
import org.joda.time.DateTime
import org.joda.time.format._
val fmt = DateTimeFormat.forPattern("dd/mm/yyyy")
val dt = fmt.parseDateTime("02/02/2017")
val fmt2 = DateTimeFormat.forPattern("yyyymmdd")
fmt2.print(dt)

How to set yesterday's date using Scala?

I am creating a date in Scala.
val dafo = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm'Z'")
val tz = TimeZone.getTimeZone("UTC")
dafo.setTimeZone(tz)
val endTime = dafo.format(new Date())
How can I set the yesterday's date instead of today's date?
Here is how you get yesterday's date/time and format it using java.time:
import java.time.{ZonedDateTime, ZoneId}
import java.time.format.DateTimeFormatter
val yesterday = ZonedDateTime.now(ZoneId.of("UTC")).minusDays(1)
val formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm'Z'")
val result = formatter format yesterday
println(result)
You can use Calendar:
val dafo = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm'Z'")
val tz = TimeZone.getTimeZone("UTC")
dafo.setTimeZone(tz)
val calendar = Calendar.getInstance()
calendar.add(Calendar.DATE, -1)
dafo.format(calendar.getTime)
JSR-310 implementation:
import java.time.OffsetDateTime
import java.time.format.DateTimeFormatter
DateTimeFormatter.ISO_INSTANT.format(OffsetDateTime.now().minusDays(1L))
Here is another alternate solution. I think its a cleaner version.
val today = java.time.LocalDate.now
today: java.time.LocalDate = 2019-12-10
val yesterday= java.time.LocalDate.now.minusDays(1)
yesterday: java.time.LocalDate = 2019-12-09

How to get current timestamp in Scala as a string without spaces?

I want to get for example a string of the current time: "20180122_101043". How can I do this?
I can create a val cal = Calendar.getInstance() but I'm not sure what to do with it after.
LocalDateTime is what you might want to use,
scala> import java.time.LocalDateTime
import java.time.LocalDateTime
scala> LocalDateTime.now()
res60: java.time.LocalDateTime = 2018-01-22T01:21:03.048
If you don't want default LocalDateTime format which is basically ISO format without zone info, you can apply DateTimeFormatter as below,
scala> import java.time.format.DateTimeFormatter
import java.time.format.DateTimeFormatter
scala> DateTimeFormatter.ofPattern("yyyy-MM-dd_HH:mm").format(LocalDateTime.now)
res61: String = 2018-01-22_01:21
Related resource - How to parse/format dates with LocalDateTime? (Java 8)
Calendar is not the best choice here. Use:
java.util.Date + java.text.SimpleDateFormat if you have java 7 or below
new SimpleDateFormat("YYYYMMdd_HHmmss").format(new Date)
java.time.LocalDateTime + java.time.format.DateTimeFormatter for java 8+
LocalDateTime.now.format(DateTimeFormatter.ofPattern("YYYYMMdd_HHmmss"))
You can make use of Java 8 Date/Time API:
import java.time.LocalDateTime
import java.time.format.DateTimeFormatter
val format = "yyyyMMdd_HHmmss"
val dtf = DateTimeFormatter.ofPattern(format)
val ldt = LocalDateTime.of(2018, 1, 22, 10, 10, 43) // 20180122_101043
ldt.format(dtf)
To get the current time, use LocalDateTime.now().
You may use the java.time library. For instance:
import java.time
val s: String = time.LocalDateTime.now().toString
println(s)
gives 2021-04-23T14:13:01.163869. Then you need to manipulate the string, e.g.
time.LocalDateTime.now().toString.replace("T","_").replace("-","").replace(":","")
for 20210423_141639.769222.

Getting a date x days back from a custom date in Scala

I have a date key of type 20170501 which is in YYYYmmdd format. How can we get a date x days back from this date in Scala?
This is what I have in program
val runDate = 20170501
Now I want a date say 30 days back from this date.
Using Scala/JVM/Java 8...
scala> import java.time._
import java.time._
scala> import java.time.format._
import java.time.format._
scala> val formatter = DateTimeFormatter.ofPattern("yyyyMMdd")
formatter: java.time.format.DateTimeFormatter = Value(YearOfEra,4,19,EXCEEDS_PAD)Value(MonthOfYear,2)Value(DayOfMonth,2)
scala> val runDate = 20170501
runDate: Int = 20170501
scala> val runDay = LocalDate.parse(runDate.toString, formatter)
runDay: java.time.LocalDate = 2017-05-01
scala> val runDayMinus30 = runDay.minusDays(30)
runDayMinus30: java.time.LocalDate = 2017-04-01
You can also use joda-time API with which has really good functions like
date.minusMonths
date.minusYear
date.minusDays
date.minusHours
date.minusMinutes
Here is simple example usinf JodaTIme API '
import org.joda.time.format.DateTimeFormat
val dtf = DateTimeFormat.forPattern("yyyyMMdd")
val dt= "20170531"
val date = dtf.parseDateTime(dt)
println(date.minusDays(30))
Output:
2017-05-01T00:00:00.000+05:45
For this you need to use udf and create a DateTime object with your input format "YYYYmmdd" and do the operations.
Hope this helps!