分数年


8

私のPPCGの休日は終わりました:D

はじめに

分数時はthe year + (the value (minute of year) / number of minutes in the year)です。

計算例

2月は常に28日で、年は常に365日であると想定する必要があります。

時間17:34 3rd March 2013を分数時間に変換したいとしましょう。まず、2013年の分数は525600分でした。これを呼び出しましょうx

次に、2013年の開始以降の経過時間を調べます。いくつかの簡単な計算から、答えは88894分であることがわかります。

今年の初めから61日が経過し、1440(1日の分数)は87840分になります。17時間で1020分(17 * 60)です。これで、87840、1020、および34分を追加して、88894分と等しくなります。

これを呼び出しましょうy

最後に、年で除算yxて年を加算すると、2013.16912小数点以下5桁になります。

入力

日付と時刻は単一の文字列として与えられます。文字列は次の形式になります。

YYYY-MM-DD hh:mm 

時間は常に24時間形式で、年は常に1900〜2050の範囲になります。

Input:  2016-08-06 23:48
Output: 2016.59723

Input:  2013-03-03 17:34
Output: 2013.16912

Input:  1914-11-11 11:11
Output: 1914.86155

報奨金を受け取る場合は、コメントまたは19バイト目でpingを送信してください。

チャレンジ

指定された日付と時刻を小数年として計算します。

すべての出力を小数点以下5桁に指定します(必要に応じて、床、天井、または真の丸めに丸めることができます)。最短のコードが勝ちます。

バウンティ

小数年形式の日付受け付け、形式で時刻を返す最短プログラムの100担当者報酬提供していYYYY-MM-DD hh:mmます。基本的に、プログラム(または関数)は次のように動作する必要があります。

f('1914-11-11 11:11') => 1914.86155
f('1914.86155')       => 1914-11-11 11:11
  1. t-clausen.dk-154バイト
  2. Neil-183バイト

リーダーボード


おそらく、日付と時刻を入力として使用すると、テストケースと簡単なチェックが可能になりますか?
Luis Mendo 2016

これがうるう年を考慮に入れているかどうかについて少し混乱していますFor this, assume February has 28 days and the year is 365 days long.が、... using the Gregorian calendar.
破壊可能なレモン

@DestructibleWatermelonいいえ、うるう年は考慮されていません
Beta Decay

小数点以下5桁以上を指定できますか?
破壊可能なレモン

@DestructibleWatermelon No
Beta Decay

回答:


1

TSQL、63バイト

最初の回答にはうるう年の計算が含まれていたため、これは私の元の回答よりも短いバージョンです。

DECLARE @ DATETIME ='2016-08-06 23:48'

PRINT LEFT(YEAR(@)+DATEDIFF(mi,0,STUFF(@,1,4,1900))/525600.,10)

フィドル

次のSQLは両方の入力タイプを処理できます

TSQL、154バイト

DECLARE @ VARCHAR(16) ='1914-11-11 11:11'--can be replaced with '1914.86155'

PRINT IIF(isdate(@)=1,LEFT(YEAR(@)+DATEDIFF(mi,0,STUFF(@,1,4,1900))/525600.,10),LEFT(@,4)+RIGHT(CONVERT(CHAR(16),DATEADD(mi,1*RIGHT(@,5)*5.256,0),20),12))

複合フィドル1

複合フィドル2


5

JavaScript(ES6)、84バイト

f=
s=>(Date.parse(1970+s.slice(4).replace(/ /,'T')+'Z')/31536e6+parseInt(s)).toFixed(5)
;
<input placeholder=Input oninput=o.value=f(this.value)><input placeholder=Output id=o>

うるう年またはDSTが不要であると仮定して、年を1970に置き換えます。これにより、1970年(または実際には他の非うるう年)Date.parseにあった時間オフセットがミリ秒単位で直接返されます31536000000。次に、年を追加して小数点以下5桁に四捨五入するだけです。編集:183 178バイトの双方向変換:

f=
s=>/:/.test(s,m=31536e6)?(Date.parse(1970+s.slice(4).replace(/ /,'T')+'Z')/m+parseInt(s)).toFixed(5):s.slice(0,4)+new Date(s.slice(4)*m+3e4).toJSON().slice(4,16).replace(/T/,' ')
;
<input placeholder=Input oninput=o.value=f(this.value)><input placeholder=Output id=o>

:上記のように処理される時刻形式の文字列を想定し、それ以外の場合は年を取り除き、ミリ秒に変換し、丸めのために30分を追加し、1970年の日付に変換し、月、日、時、分を抽出し、元の年。


@βετѧΛєҫαγはい、s関数への引数です。
Neil

これは無効な出力を提供しませんか?チャレンジは明示的に2月に28日、合計で365日のみとなるように要求するためです。
AdmBorkBork 16

@TimmyDの2月は29日になることがあります。うるう年を正しく処理することが禁止されているわけではないと仮定ましょう
t-clausen.dk

@ t-clausen.dk申し訳ありませんが、うるう年は処理しないことを意味していました
Beta Decay

@βετѧΛєҫαγうるう年もDSTも使用しないようになり、リバーシブルバージョンも使用できるようになりました。それで満足ですか?
ニール

2

Matlab、132 115バイト

 d=input('');m=cumsum([-1 '# #"#"##"#"'-4]);year(d)+fix((((m(month(d))+day(d))*24+hour(d))*60+minute(d))/5.256)/10^5

0に向かって丸めます。

うーん...それはかなり長いです。
うるう年のために、それはいくつかの組み込み関数を使用していますが、実際に役立つものではありません。

文字列を直接解析すると、さらに2バイトの解決策が得られます。

d=sscanf(input(''),'%d%[- :]');m=cumsum([-1 '# #"#"##"#"'-4]);d(1)+fix((((m(d(3))+d(5))*24+d(7))*60+d(9))/5.256)/10^5

新しいMatlabバージョンにはおそらくより良い分割機能がありますが、私は2012aで​​実行しています。

@Luis Mendoのおかげでいくつかのバイトが節約されました


[-1 '# #"#"##"#"'-4]数バイトを節約するために配列を定義できます。あるyearなどの標準的な機能は?ツールボックスを使用している場合は、タイトルにそのことを示す必要があります。たとえば、「Matlab with Financial Toolbox」
Luis Mendo

@LuisMendo私は-表記に慣れておらず、#それに遭遇したことすらありません。詳細はどこで確認できますか?yearなどは標準的な機能だと思いますが、ツールボックス(ドキュメント)外で同じように動作するかどうかはわかりません。
pajonk

特別な表記ではありません。これは、必要な数値を生成するための適切なASCIIコードを持つ文字列です。機能に関しては、明確にしてくれてありがとう。Matlab 15bにはないようです
Luis Mendo

ああ、それは賢いです。
pajonk

1

PowerShell v3 +、131バイト

$t=date $args[0];$a=1440*!!(date "2-29-$($t.year)");"{0:F5}"-f((($t.DayOfYear-1)*1440+$t.TimeOfDay.TotalMinutes-$a)/525600+$t.Year)

入力を受け取り$args[0]、それをGet-Date.NET [datetime]形式に保存するために変換し、に保存します$t。2月29日が存在するかどうかを計算$aし、その日付の分(存在する場合)を差し引くように設定します。

次に、10進数5桁の固定文字列を指定-fしたormat演算子を使用して、計算を実行します。組み込み関数を使用して、指定された入力のおよびを計算し、うるう年である場合は減算し、合計分数で割り、入力を追加します。.DayOfYear.TotalMinutes$a525600.Year

2月29日が存在しない場合は(詳細に)STDERRに文句を言いますが(以下の例を参照)、STDERRはデフォルトで無視されるため、心配する必要はありません。また、PowerShellはデフォルトで銀行の丸めを行うことに注意してください。

PS C:\Tools\Scripts\golfing> .\fractional-year.ps1 '2016-08-06 23:48'
2016.59724

PS C:\Tools\Scripts\golfing> .\fractional-year.ps1 '2013-03-03 17:34'
Get-Date : Cannot bind parameter 'Date'. Cannot convert value "2-29-2013" to type "System.DateTime". Error: "String was not recognized as a valid DateTime."
At C:\Tools\Scripts\golfing\fractional-year.ps1:7 char:36
+   $t=date $args[0];$a=1440*!!(date "2-29-$($t.year)");"{0:F5}"-f((($t.DayOfYear- ...
+                                    ~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidArgument: (:) [Get-Date], ParameterBindingException
    + FullyQualifiedErrorId : CannotConvertArgumentNoMessage,Microsoft.PowerShell.Commands.GetDateCommand

2013.16913

PS C:\Tools\Scripts\golfing> .\fractional-year.ps1 '1914-11-11 11:11'
Get-Date : Cannot bind parameter 'Date'. Cannot convert value "2-29-1914" to type "System.DateTime". Error: "String was not recognized as a valid DateTime."
At C:\Tools\Scripts\golfing\fractional-year.ps1:7 char:36
+   $t=date $args[0];$a=1440*!!(date "2-29-$($t.year)");"{0:F5}"-f((($t.DayOfYear- ...
+                                    ~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidArgument: (:) [Get-Date], ParameterBindingException
    + FullyQualifiedErrorId : CannotConvertArgumentNoMessage,Microsoft.PowerShell.Commands.GetDateCommand

1914.86155

または、うるう年では119バイト

"{0:F5}"-f((($t=date $args[0]).DayOfYear-1+$t.TimeOfDay.TotalMinutes/1440)/(date "12-31-$($t.year)").DayOfYear+$t.Year)

カレンダーの設定に従う$aと、上記の元のコードで説明する必要がないため、1ダースのバイトを削減できます。これにより$t、式自体に移動でき.DayOfYear、12月31日のを明示的に計算します。それ以外の場合は、同じ方法に従います。


0

Python 3、163 173バイト

出力フォーマットのためにバイトが増える

Javaの回答のように、組み込みの日付を使用しません。

def s(x):z=x[5:10].split("-");v=x[10:].split(":");return int(x[:4])+(sum(([-1,31,28]+[31,30,31,30,31]*2)[:int(z[0])],int(z[1]))*1440+int(v[0])*60+int(v[1]))/525600

少し読みやすい

def s(x):
    date=x[5:10].split("-");time=x[10:].split(":")
    return int(x[:4])+(sum(([-1,31,28]+[31,30,31,30,31]*2)[:int(date[0])],int(date[1]))*1440+int(time[0])*60+int(time[1]))/525600

0

Perl 6の 107の105  102バイト

{$/=.comb(/\d+/);($0+(sum(|flat(-1,31,28,(31,30,31,30,31)xx 2)[^$1],$2)*1440+$3*60+$4)/525600).fmt: '%.5f'}
{$/=.comb(/\d+/);fmt $0+(sum(|flat(-1,31,28,(31,30,31,30,31)xx 2)[^$1],$2)*1440+$3*60+$4)/525600: '%.5f'}

{$/=.comb(/\d+/);fmt $0+(flat($2-1,31,28,(31,30,31,30,31)xx 2)[^$1].sum*1440+$3*60+$4)/525600: '%.5f'}
{$/=.comb(/\d+/);round $0+(flat($2-1,31,28,(31,30,31,30,31)xx 2)[^$1].sum*1440+$3*60+$4)/525600,.1⁵}

説明:

{
  $/ = .comb(/\d+/); # grab a list of only the digits
  # 「$0」 is short for 「$/[0]」

  fmt

    $0 # year
    +
    (
      flat(
        $2 -1,                     #    days
        31,28,(31,30,31,30,31)xx 2 # -+ months
      )[^$1].sum * 1440            # /
      + $3 * 60                    #    hours
      + $4                         #    minutes
    )
    /
    525600

  : '%.5f' # the 「:」 is used here as 「fmt」 is a method not a subroutine
}

テスト:

#! /usr/bin/env perl6
use v6.c;
use Test;

# returns Str
my &fractional-year-a = {$/=.comb(/\d+/);fmt $0+(sum(flat($2-1,31,28,(31,30,31,30,31)xx 2)[^$1])*1440+$3*60+$4)/525600: '%.5f'}
# returns Rat
my &fractional-year-b = {$/=.comb(/\d+/);round $0+(sum(flat($2-1,31,28,(31,30,31,30,31)xx 2)[^$1])*1440+$3*60+$4)/525600,.1⁵}

my @tests = (
  '2016-08-06 23:48' => 2016.59723,
  '2013-03-03 17:34' => 2013.16912,
  '1914-11-11 11:11' => 1914.86155,
);

plan +@tests * 2;

for @tests -> $_ ( :key($input), :value($expected) ) {
  is-approx +fractional-year-a($input), +$expected, 1e-5, "a $input => $expected";
  is-approx +fractional-year-b($input), +$expected, 1e-5, "b $input => $expected";
}
1..6
ok 1 - a 2016-08-06 23:48 => 2016.59723
ok 2 - b 2016-08-06 23:48 => 2016.59723
ok 3 - a 2013-03-03 17:34 => 2013.16912
ok 4 - b 2013-03-03 17:34 => 2013.16912
ok 5 - a 1914-11-11 11:11 => 1914.86155
ok 6 - b 1914-11-11 11:11 => 1914.86155
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.