DEV Community

Myoungjin Jeon
Myoungjin Jeon

Posted on • Edited on

[Short Prog] Week Number Getter

The one way to store my weekly documents in a directory or a weekly task in a spreadsheet is to store them into a separate directory (or a sheet) by weekly basis. and I used the week number because it has shorter name than using period notation like (08.02-08.08).
I scanned some invoices and name it in sort of "20210805.Chicken.pdf" then I move them into appropriate "week -number-ed" directory.
then I realised that there might be some automatic way to put them into matched weekly directory.

How to get week number in Raku

I'm a raku user. and I could make it a simple terminal interface programme like below.

#!/usr/bin/env raku multi sub MAIN ( Int $year, Int $month, Int $day ) { say Date.new( :$year, :$month, :$day ).week-number(); } 
Enter fullscreen mode Exit fullscreen mode
> chmod u+x week-number.raku > week-number.raku 2021 8 4 31 
Enter fullscreen mode Exit fullscreen mode

I think it's pretty straight forward if get used to some syntax.

If you want to use a single text like "20210804"
I could add one more multi sub for the MAIN()

sub cut-off-last-two-digits( @i ) returns Int { # warning: side effect ( @i.pop, @i.pop ).reverse.join.Int } multi sub MAIN ( Int \yyyymmdd ) { my @i = yyyymmdd.comb; my ( $year, $month, $day ); $day = cut-off-last-two-digits @i; $month = cut-off-last-two-digits @i; $year = @i.join.Int; if (( $year, $month, $day )>>.defined).any == False { die "check your input: {yyyymmdd}"; } samewith( $year, $month, $day ); } multi sub MAIN ( Int $year, Int $month, Int $day ) { say Date.new( :$year, :$month, :$day ).week-number(); } 
Enter fullscreen mode Exit fullscreen mode

Perl5 Version

I searched the internet and I used DateTime module to implement.
but I guess DateTime is quite heavy module. because perl is normally very very fast but this programme isn't.

#!/usr/bin/env perl use strict; use warnings; use v5.26; use DateTime; use File::Basename; our $PROG = $0; my @parsed; my ( $year, $month, $day ); use enum qw(F_YEAR F_MONTH F_DAY); sub usage { print << 'END_OF_USAGE'; $PROG <YYYYMMDD> OR $PROG <YYYY> <MM> <DD> END_OF_USAGE } if ( @ARGV == 1 ) { # parse as YYYYMMDD my $str = $ARGV[0]; @parsed = $str =~ /^(\d+)(\d\d)(\d\d)$/; } elsif ( @ARGV == 3 ) { @parsed = @ARGV; } else { usage(); exit 1; } ( $year, $month, $day ) = @parsed[F_YEAR, F_MONTH, F_DAY]; my $dt = DateTime->new( year => $year, month => $month, day => $day ); print $dt->week_number(); 
Enter fullscreen mode Exit fullscreen mode

Haskell Version

I still hate some part of code and there is no proper way to handle errors but it is working fast. so I'm going to stick with this programme for a while.

> stack new week-number 
Enter fullscreen mode Exit fullscreen mode

app/Main.hs

module Main where import System.Environment import Lib main :: IO () main = do args <- getArgs -- note: args :: [String] putStrLn (case args of yyyymmdd:[] -> weekNumberStringFromString yyyymmdd y:m:d:[] -> let y' = (read y :: Integer) m' = (read m :: Int) d' = (read d :: Int) in weekNumberStringFromGregorian y' m' d' _ -> unlines [ "usage:" , "week-number: <yyyymmdd>" , " or" , "week-number: <yyyy> <m> <d>" ] ) 
Enter fullscreen mode Exit fullscreen mode

src/Lib.hs

module Lib ( weekNumberStringFromString , weekNumberStringFromGregorian ) where import qualified Data.Time as DT weekNumberStringFromString :: String -> String weekNumberStringFromString yyyymmdd = let ut = DT.parseTimeOrError True DT.defaultTimeLocale "%Y%m%d" yyyymmdd :: DT.UTCTime in DT.formatTime DT.defaultTimeLocale "%V" ut weekNumberStringFromGregorian :: Integer -> Int -> Int -> String weekNumberStringFromGregorian y m d = ( DT.formatTime DT.defaultTimeLocale "%V" ) $ DT.fromGregorian y m d 
Enter fullscreen mode Exit fullscreen mode
> stack build > stack install > week-number-exe 2021 8 4 31 
Enter fullscreen mode Exit fullscreen mode

so now I need to make some script go through the file
and get the date information from the file name and move them into
right place.

Okay. That's all today.

Top comments (0)