매월 첫째 날과 마지막 날

매월 첫째 날과 마지막 날

월과 연도라는 두 개의 숫자가 주어지면 해당 월의 첫 번째 날과 마지막 날을 어떻게 계산합니까? 내 목표는 다음 세 줄을 출력하는 것입니다.

  1. Month/Year (월은 텍스트 형식이지만 간단합니다.)

  2. 매월 각 날짜: 해당 날짜는 요일의 이름입니다: 금요일. & 토요일. & 해. [...]

  3. 월의 일수: 1 & 2 & 3 [...] & 28 & .. ?

dateGNU 또는 BSD date(OS X) 를 사용하는 솔루션을 찾고 있습니다 .

답변1

# Last month:
l_first_date=$(date -d "`date +%Y%m01` -1 month" +%Y-%m-%d)
l_last_date=$(date -d "`date +%Y%m01` -1 day" +%Y-%m-%d)

# This month:
t_first_date=$(date +%Y-%m-01)
t_last_date=$(date -d "`date +%Y%m01` +1 month -1 day" +%Y-%m-%d)

# Next month:
n_first_date=$(date -d "`date +%Y%m01` +1 month" +%Y-%m-%d)
n_last_date=$(date -d "`date +%Y%m01` +2  month -1 day" +%Y-%m-%d)

# Print everything
echo "Last month: $l_first_date to $l_last_date"
echo "This month: $t_first_date to $t_last_date"
echo "Next month: $n_first_date to $n_last_date"

답변2

솔직하게 말씀드리자면, 질문하신 내용을 보면 숙제가 좀 있는 것 같습니다. 따라서 독자를 위한 연습으로 답변에 몇 가지 단계를 남겨 두겠습니다.

date맨페이지를 주의 깊게 살펴보는 것이 좋습니다 . 특히 -d특정 날짜를 확인할 수 있는 플래그를 살펴보세요. Y 연도 M 월의 첫 번째 날은 "M/01/Y"입니다.

얻다마지막월의 일, 가장 좋은 방법은 주어진 월 숫자에 1을 더한 다음 날짜에서 일을 빼는 것입니다.

힌트: 실제로는 광범위한 산술을 받아들이는 것이 가능합니다. 예를 들어, 그것이 나에게 정답을 줄 것이라고 date말할 수 있습니다 .date -d "01/07/2012 + 1 month - 1 day"

date맨페이지의 "형식" 섹션을 살펴보면 2)와 3)에서 원하는 출력을 표시하는 방법을 배울 수 있습니다.

팁: 보기 %a%d

답변3

저도 얼마전에 비슷한 문제를 겪었습니다. 내 솔루션은 다음과 같습니다

 $ ./get_dates.sh 2012 07
The first day is 01.2012.07, Sunday
The last day is 31.2012.07, Tuesday
 $ cal
 July 2012
Su Mo Tu We Th Fr Sa
 1  2  3  4  5  6  7
 8  9 10 11 12 13 14
15 16 17 18 19 20 21
22 23 24 25 26 27 28
29 30 31

스크립트 자체:

#!/bin/bash
# last day for month
lastday()  {
#                ja   fe   ma   ap   ma   jn   jl   ag   se   oc   no   de
  mlength=('xx' '31' '28' '31' '30' '31' '30' '31' '31' '30' '31' '30' '31')

  year=$1
  month=$2

  if [ $month -ne 2 ] ; then
    echo ${mlength[$month]}
    return 0
  fi

  leap=0
  ((!(year%100))) && { ((!(year%400))) && leap=1 ; } || { ((!(year%4))) && leap=1 ; }

  feblength=28
  ((leap)) && feblength=29
  echo $feblength
}

# date to Julian date
date2jd() {

  year=$1
  month=$2
  day=$3
  lday=$(lastday $year $month) || exit $?

  if ((day<1 || day> lday)) ; then
    echo day out of range
    exit 1
  fi

  echo $(( jd = day - 32075
                + 1461 * (year + 4800 - (14 - month)/12)/4
                        + 367 * (month - 2 + (14 - month)/12*12)/12
                    - 3 * ((year + 4900 - (14 - month)/12)/100)/4
                - 2400001 ))
}

jd2dow()
{
  days=('Sunday' 'Monday' 'Tuesday' 'Wednesday' 'Thursday' 'Friday' 'Saturday')

  jd=$1
  if ((jd<1 || jd>782028)) ; then
    echo julian day out of range
    return 1
  fi

  ((dow=(jd+3)%7))

  echo ${days[dow]}
}


echo -n "The first day is 01.$1.$2, "
jd2dow $(date2jd $1 $2 01)
echo -n "The last day is $(lastday $1 $2).$1.$2, "
jd2dow $(date2jd $1 $2 $(lastday $1 $2))

필요한 컴퓨터에 GNU가 없으므로 date날짜로 해결하지 않습니다. 어쩌면 더 좋은 해결책이 있을 수도 있습니다.

답변4

지난달의 시작일과 종료일

month_year=$(date +'%m %Y' | awk '!--$1{$1=12;$2--}1')
m=${month_year% *}
y=${month_year##* }
d=$(cal $m $y | paste -s - | awk '{print $NF}')
first_date=$(printf '01-%02s-%s' $m $y)
last_date=$(printf '%s-%02s-%s' $d $m $y)
echo $first_date $last_date

해당 월의 시작일과 종료일

month_year=$(date +'%m %Y' | awk '!$1{$1=12;$2--}1')
m=${month_year% *}
y=${month_year##* }
d=$(cal $m $y | paste -s - | awk '{print $NF}')
first_date=$(printf '01-%02s-%s' $m $y)
last_date=$(printf '%s-%02s-%s' $d $m $y)
echo $first_date $last_date

다음 달 시작일 및 종료일

month_year=$(date +'%m %Y' | awk '!++$1{$1=12;$2--}1')
m=${month_year% *}
y=${month_year##* }
d=$(cal $m $y | paste -s - | awk '{print $NF}')
first_date=$(printf '01-%02s-%s' $m $y)
last_date=$(printf '%s-%02s-%s' $d $m $y)
echo $first_date $last_date

관련 정보