繁体   English   中英

C# 带纬度/经度的日出/日落

[英]C# Sunrise/Sunset with latitude/longitude

C# 中有没有一种方法可以计算给定的纬度和经度,当太阳在给定的一天落下和升起时?

Javascript计算 这里 现在你只需要移植。


编辑:现在计算在此页面的源代码中。


编辑: 是源代码的直接链接。 无需通过html进行搜索。

我知道这篇文章很老,但万一有人还在看...

CoordinateSharp作为Nuget包提供。 它是一个独立的包装,可以处理太阳和月亮时间。

Celestial cel = Celestial.CalculateCelestialTimes(85.57682, -70.75678, new DateTime(2017,8,21));
Console.WriteLine(cel.SunRise.Value.ToString());

注意:

它假设DateTimes始终是UTC。

最后,如果日期返回null,您可能需要引用太阳/月亮天体.Condition 当太阳全天上升/下降时会发生这种情况。

编辑1/9/2019

自此帖以来,图书馆发生了巨大变化。 它现在也可以处理当地时间。

我用NAA javascript和c#在C#中创建了这个库。

C#中的日出和日落

我对这两个网站进行了测试,它显示的时间与网站完全一样。

http://www.timeanddate.com/sun/usa/seattle

http://www.esrl.noaa.gov/gmd/grad/solcalc/

这个API似乎对我有用:

http://sunrise-sunset.org/api

接受的答案是JavaScript实现,它不适合我的应用程序,因为我需要在C#中进行计算。

我已经使用了这个C#代码: http//wiki.crowe.co.nz/Calculate%20Sunrise%2fSunset.ashx ,我已经在这里验证了日出/日落时间: http//www.timeanddate.com/天文学/

如果我将秒数舍入到最近的分钟,则C#实现的日出和日落时间与timeanddate.com上显示的相应值相匹配,包括夏令时。 虽然代码有点压倒性的(除非你也喜欢月相数据),所以我将重构它,以便具体完成我现在需要的数字是正确的。

我做了一个快速的Python脚本: SunriseSunsetCalculator

我还没有将它包装在一个类中,但它可能对其他人有用。


编辑:开源很棒,因为提交基本脚本,有人将其包装在一个模块中,另一个添加了一个cli界面! 感谢mbideau和nfischer的贡献!

dot.答案的VB.Net版本,它也可以自动确定时区。

输出(通过观看今晚的日落来检查):

产量

Main.VB:

Module Main

Sub Main()

    ' http://www.timeanddate.com/sun/usa/seattle
    ' http://www.esrl.noaa.gov/gmd/grad/solcalc/

    ' Vessy, Switzerland
    Dim latitude As Double = 46.17062
    Dim longitude As Double = 6.161667
    Dim dst As Boolean = True
    Dim timehere As DateTime = DateTime.Now

    Console.WriteLine("It is currently {0:HH:mm:ss} UTC", DateTime.UtcNow)
    Console.WriteLine("The time here, at {0}°,{1}° is {2:HH:mm:ss}", latitude, longitude, timehere)
    Dim local As TimeZoneInfo = TimeZoneInfo.Local
    Dim zone As Integer = local.BaseUtcOffset().TotalHours

    If local.SupportsDaylightSavingTime Then
        Dim standard As String = local.StandardName
        Dim daylight As String = local.DaylightName
        dst = local.IsDaylightSavingTime(timehere)
        Dim current As String = IIf(dst, daylight, standard)
        Console.WriteLine("Daylight-saving time is supported here. Current offset {0:+0} hours, {1}", zone, current)
    Else
        Console.WriteLine("Daylight-saving time is not supported here")
    End If

    System.Console.WriteLine("Sunrise today {0}", Sunrises(latitude, longitude))
    System.Console.WriteLine("Sunset  today {0}", Sunsets(latitude, longitude))
    System.Console.ReadLine()
End Sub

End Module

Sun.vb:

Public Module Sun
' Get sunrise time at latitude, longitude using local system timezone
Function Sunrises(latitude As Double, longitude As Double) As DateTime
    Dim julian As Double = JulianDay(DateTime.Now)
    Dim rises As Double = SunRiseUTC(julian, latitude, longitude)
    Dim timehere As DateTime = DateTime.Now
    Dim local As TimeZoneInfo = TimeZoneInfo.Local
    Dim dst As Boolean = local.IsDaylightSavingTime(timehere)
    Dim zone As Integer = local.BaseUtcOffset().TotalHours
    Dim result As DateTime = getDateTime(rises, zone, timehere, dst)
    Return result
End Function
' Get sunset time at latitude, longitude using local system timezone
Function Sunsets(latitude As Double, longitude As Double) As DateTime
    Dim julian As Double = JulianDay(DateTime.Now)
    Dim rises As Double = SunSetUTC(julian, latitude, longitude)
    Dim timehere As DateTime = DateTime.Now
    Dim local As TimeZoneInfo = TimeZoneInfo.Local
    Dim dst As Boolean = local.IsDaylightSavingTime(timehere)
    Dim zone As Integer = local.BaseUtcOffset().TotalHours
    Dim result As DateTime = getDateTime(rises, zone, timehere, dst)
    Return result
End Function
' Convert radian angle to degrees
Public Function Degrees(angleRad As Double) As Double
    Return (180.0 * angleRad / Math.PI)
End Function
' Convert degree angle to radians
Public Function Radians(angleDeg As Double) As Double
    Return (Math.PI * angleDeg / 180.0)
End Function
'* Name: JulianDay  
'* Type: Function   
'* Purpose: Julian day from calendar day    
'* Arguments:   
'* year : 4 digit year  
'* month: January = 1   
'* day : 1 - 31 
'* Return value:    
'* The Julian day corresponding to the date 
'* Note:    
'* Number is returned for start of day. Fractional days should be   
'* added later. 
Public Function JulianDay(year As Integer, month As Integer, day As Integer) As Double
    If month <= 2 Then
        year -= 1
        month += 12
    End If
    Dim A As Double = Math.Floor(year / 100.0)
    Dim B As Double = 2 - A + Math.Floor(A / 4)

    Dim julian As Double = Math.Floor(365.25 * (year + 4716)) + Math.Floor(30.6001 * (month + 1)) + day + B - 1524.5
    Return julian
End Function

Public Function JulianDay([date] As DateTime) As Double
    Return JulianDay([date].Year, [date].Month, [date].Day)
End Function

'***********************************************************************/
'* Name: JulianCenturies    
'* Type: Function   
'* Purpose: convert Julian Day to centuries since J2000.0.  
'* Arguments:   
'* julian : the Julian Day to convert   
'* Return value:    
'* the T value corresponding to the Julian Day  
'***********************************************************************/

Public Function JulianCenturies(julian As Double) As Double
    Dim T As Double = (julian - 2451545.0) / 36525.0
    Return T
End Function


'***********************************************************************/
'* Name: JulianDayFromJulianCentury 
'* Type: Function   
'* Purpose: convert centuries since J2000.0 to Julian Day.  
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* the Julian Day corresponding to the t value  
'***********************************************************************/

Public Function JulianDayFromJulianCentury(t As Double) As Double
    Dim julian As Double = t * 36525.0 + 2451545.0
    Return julian
End Function


'***********************************************************************/
'* Name: calGeomMeanLongSun 
'* Type: Function   
'* Purpose: calculate the Geometric Mean Longitude of the Sun   
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* the Geometric Mean Longitude of the Sun in degrees   
'***********************************************************************/

Public Function GemoetricMeanLongitude(t As Double) As Double
    Dim L0 As Double = 280.46646 + t * (36000.76983 + 0.0003032 * t)
    While L0 > 360.0
        L0 -= 360.0
    End While
    While L0 < 0.0
        L0 += 360.0
    End While
    Return L0
    ' in degrees
End Function


'***********************************************************************/
'* Name: calGeomAnomalySun  
'* Type: Function   
'* Purpose: calculate the Geometric Mean Anomaly of the Sun 
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* the Geometric Mean Anomaly of the Sun in degrees 
'***********************************************************************/

Public Function GemoetricMeanAnomaly(t As Double) As Double
    Dim M As Double = 357.52911 + t * (35999.05029 - 0.0001537 * t)
    Return M
    ' in degrees
End Function

'***********************************************************************/
'* Name: EarthOrbitEccentricity 
'* Type: Function   
'* Purpose: calculate the eccentricity of earth's orbit 
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* the unitless eccentricity    
'***********************************************************************/


Public Function EarthOrbitEccentricity(t As Double) As Double
    Dim e As Double = 0.016708634 - t * (0.000042037 + 0.0000001267 * t)
    Return e
    ' unitless
End Function

'***********************************************************************/
'* Name: SunCentre  
'* Type: Function   
'* Purpose: calculate the equation of center for the sun    
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* in degrees   
'***********************************************************************/


Public Function SunCentre(t As Double) As Double
    Dim m As Double = GemoetricMeanAnomaly(t)

    Dim mrad As Double = Radians(m)
    Dim sinm As Double = Math.Sin(mrad)
    Dim sin2m As Double = Math.Sin(mrad + mrad)
    Dim sin3m As Double = Math.Sin(mrad + mrad + mrad)

    Dim C As Double = sinm * (1.914602 - t * (0.004817 + 0.000014 * t)) + sin2m * (0.019993 - 0.000101 * t) + sin3m * 0.000289
    Return C
    ' in degrees
End Function

'***********************************************************************/
'* Name: SunTrueLongitude   
'* Type: Function   
'* Purpose: calculate the true longitude of the sun 
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* sun's true longitude in degrees  
'***********************************************************************/


Public Function SunTrueLongitude(t As Double) As Double
    Dim l0 As Double = GemoetricMeanLongitude(t)
    Dim c As Double = SunCentre(t)

    Dim O As Double = l0 + c
    Return O
    ' in degrees
End Function

'***********************************************************************/
'* Name: SunTrueAnomaly 
'* Type: Function   
'* Purpose: calculate the true anamoly of the sun   
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* sun's true anamoly in degrees    
'***********************************************************************/

Public Function SunTrueAnomaly(t As Double) As Double
    Dim m As Double = GemoetricMeanAnomaly(t)
    Dim c As Double = SunCentre(t)

    Dim v As Double = m + c
    Return v
    ' in degrees
End Function

'***********************************************************************/
'* Name: SunDistanceAU  
'* Type: Function   
'* Purpose: calculate the distance to the sun in AU 
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* sun radius vector in AUs 
'***********************************************************************/

Public Function SunDistanceAU(t As Double) As Double
    Dim v As Double = SunTrueAnomaly(t)
    Dim e As Double = EarthOrbitEccentricity(t)

    Dim R As Double = (1.000001018 * (1 - e * e)) / (1 + e * Math.Cos(Radians(v)))
    Return R
    ' in AUs
End Function

'***********************************************************************/
'* Name: SunApparentLongitude   
'* Type: Function   
'* Purpose: calculate the apparent longitude of the sun 
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* sun's apparent longitude in degrees  
'***********************************************************************/

Public Function SunApparentLongitude(t As Double) As Double
    Dim o As Double = SunTrueLongitude(t)

    Dim omega As Double = 125.04 - 1934.136 * t
    Dim lambda As Double = o - 0.00569 - 0.00478 * Math.Sin(Radians(omega))
    Return lambda
    ' in degrees
End Function

'***********************************************************************/
'* Name: MeanObliquityOfEcliptic    
'* Type: Function   
'* Purpose: calculate the mean obliquity of the ecliptic    
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* mean obliquity in degrees    
'***********************************************************************/

Public Function MeanObliquityOfEcliptic(t As Double) As Double
    Dim seconds As Double = 21.448 - t * (46.815 + t * (0.00059 - t * (0.001813)))
    Dim e0 As Double = 23.0 + (26.0 + (seconds / 60.0)) / 60.0
    Return e0
    ' in degrees
End Function

'***********************************************************************/
'* Name: calcObliquityCorrection    
'* Type: Function   
'* Purpose: calculate the corrected obliquity of the ecliptic   
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* corrected obliquity in degrees   
'***********************************************************************/

Public Function calcObliquityCorrection(t As Double) As Double
    Dim e0 As Double = MeanObliquityOfEcliptic(t)

    Dim omega As Double = 125.04 - 1934.136 * t
    Dim e As Double = e0 + 0.00256 * Math.Cos(Radians(omega))
    Return e
    ' in degrees
End Function

'***********************************************************************/
'* Name: SunRightAscension  
'* Type: Function   
'* Purpose: calculate the right ascension of the sun    
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* sun's right ascension in degrees 
'***********************************************************************/

Public Function SunRightAscension(t As Double) As Double
    Dim e As Double = calcObliquityCorrection(t)
    Dim lambda As Double = SunApparentLongitude(t)

    Dim tananum As Double = (Math.Cos(Radians(e)) * Math.Sin(Radians(lambda)))
    Dim tanadenom As Double = (Math.Cos(Radians(lambda)))
    Dim alpha As Double = Degrees(Math.Atan2(tananum, tanadenom))
    Return alpha
    ' in degrees
End Function

'***********************************************************************/
'* Name: SunDeclination 
'* Type: Function   
'* Purpose: calculate the declination of the sun    
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* sun's declination in degrees 
'***********************************************************************/

Public Function SunDeclination(t As Double) As Double
    Dim e As Double = calcObliquityCorrection(t)
    Dim lambda As Double = SunApparentLongitude(t)

    Dim sint As Double = Math.Sin(Radians(e)) * Math.Sin(Radians(lambda))
    Dim theta As Double = Degrees(Math.Asin(sint))
    Return theta
    ' in degrees
End Function

'***********************************************************************/
'* Name: TrueSolarToMeanSolar   
'* Type: Function   
'* Purpose: calculate the difference between true solar time and mean   
'*   solar time 
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* Return value:    
'* equation of time in minutes of time  
'***********************************************************************/

Public Function TrueSolarToMeanSolar(t As Double) As Double
    Dim epsilon As Double = calcObliquityCorrection(t)
    Dim l0 As Double = GemoetricMeanLongitude(t)
    Dim e As Double = EarthOrbitEccentricity(t)
    Dim m As Double = GemoetricMeanAnomaly(t)

    Dim y As Double = Math.Tan(Radians(epsilon) / 2.0)
    y *= y

    Dim sin2l0 As Double = Math.Sin(2.0 * Radians(l0))
    Dim sinm As Double = Math.Sin(Radians(m))
    Dim cos2l0 As Double = Math.Cos(2.0 * Radians(l0))
    Dim sin4l0 As Double = Math.Sin(4.0 * Radians(l0))
    Dim sin2m As Double = Math.Sin(2.0 * Radians(m))

    Dim Etime As Double = y * sin2l0 - 2.0 * e * sinm + 4.0 * e * y * sinm * cos2l0 - 0.5 * y * y * sin4l0 - 1.25 * e * e * sin2m

    Return Degrees(Etime) * 4.0
    ' in minutes of time
End Function

'***********************************************************************/
'* Name: SunriseHourAngle   
'* Type: Function   
'* Purpose: calculate the hour angle of the sun at sunrise for the  
'*   latitude   
'* Arguments:   
'* lat : latitude of observer in degrees    
'*  solarDec : declination angle of sun in degrees  
'* Return value:    
'* hour angle of sunrise in radians 
'***********************************************************************/

Public Function SunriseHourAngle(lat As Double, solarDec As Double) As Double
    Dim latRad As Double = Radians(lat)
    Dim sdRad As Double = Radians(solarDec)

    Dim HAarg As Double = (Math.Cos(Radians(90.833)) / (Math.Cos(latRad) * Math.Cos(sdRad)) - Math.Tan(latRad) * Math.Tan(sdRad))

    Dim HA As Double = (Math.Acos(Math.Cos(Radians(90.833)) / (Math.Cos(latRad) * Math.Cos(sdRad)) - Math.Tan(latRad) * Math.Tan(sdRad)))

    Return HA
    ' in radians
End Function

'***********************************************************************/
'* Name: SunsetHourAngle    
'* Type: Function   
'* Purpose: calculate the hour angle of the sun at sunset for the   
'*   latitude   
'* Arguments:   
'* lat : latitude of observer in degrees    
'*  solarDec : declination angle of sun in degrees  
'* Return value:    
'* hour angle of sunset in radians  
'***********************************************************************/

Public Function SunsetHourAngle(lat As Double, solarDec As Double) As Double
    Dim latRad As Double = Radians(lat)
    Dim sdRad As Double = Radians(solarDec)

    Dim HAarg As Double = (Math.Cos(Radians(90.833)) / (Math.Cos(latRad) * Math.Cos(sdRad)) - Math.Tan(latRad) * Math.Tan(sdRad))

    Dim HA As Double = (Math.Acos(Math.Cos(Radians(90.833)) / (Math.Cos(latRad) * Math.Cos(sdRad)) - Math.Tan(latRad) * Math.Tan(sdRad)))

    Return -HA
    ' in radians
End Function


'***********************************************************************/
'* Name: SunRiseUTC 
'* Type: Function   
'* Purpose: calculate the Universal Coordinated Time (UTC) of sunrise   
'*   for the given day at the given location on earth   
'* Arguments:   
'* julian : julian day  
'* latitude : latitude of observer in degrees   
'* longitude : longitude of observer in degrees 
'* Return value:    
'* time in minutes from zero Z  
'***********************************************************************/

'Public  Function SunRiseUTC(julian As Double, latitude As Double, longitude As Double) As Double
'    Dim t As Double = JulianCenturies(julian)

'    ' *** Find the time of solar noon at the location, and use
'    ' that declination. This is better than start of the 
'    ' Julian day

'    Dim noonmin As Double = SolarNoonUTC(t, longitude)
'    Dim tnoon As Double = JulianCenturies(julian + noonmin / 1440.0)

'    ' *** First pass to approximate sunrise (using solar noon)

'    Dim eqTime As Double = TrueSolarToMeanSolar(tnoon)
'    Dim solarDec As Double = SunDeclination(tnoon)
'    Dim hourAngle As Double = SunriseHourAngle(latitude, solarDec)

'    Dim delta As Double = longitude - Degrees(hourAngle)
'    Dim timeDiff As Double = 4 * delta
'    ' in minutes of time
'    Dim timeUTC As Double = 720 + timeDiff - eqTime
'    ' in minutes
'    ' alert("eqTime = " + eqTime + "\nsolarDec = " + solarDec + "\ntimeUTC = " + timeUTC);

'    ' *** Second pass includes fractional julianay in gamma calc

'    Dim newt As Double = JulianCenturies(JulianDayFromJulianCentury(t) + timeUTC / 1440.0)
'    eqTime = TrueSolarToMeanSolar(newt)
'    solarDec = SunDeclination(newt)
'    hourAngle = SunriseHourAngle(latitude, solarDec)
'    delta = longitude - Degrees(hourAngle)
'    timeDiff = 4 * delta
'    timeUTC = 720 + timeDiff - eqTime
'    ' in minutes
'    ' alert("eqTime = " + eqTime + "\nsolarDec = " + solarDec + "\ntimeUTC = " + timeUTC);

'    Return timeUTC
'End Function

'***********************************************************************/
'* Name: SolarNoonUTC   
'* Type: Function   
'* Purpose: calculate the Universal Coordinated Time (UTC) of solar 
'*   noon for the given day at the given location on earth  
'* Arguments:   
'* t : number of Julian centuries since J2000.0 
'* longitude : longitude of observer in degrees 
'* Return value:    
'* time in minutes from zero Z  
'***********************************************************************/

Public Function SolarNoonUTC(t As Double, longitude As Double) As Double
    ' First pass uses approximate solar noon to calculate eqtime
    Dim tnoon As Double = JulianCenturies(JulianDayFromJulianCentury(t) + longitude / 360.0)
    Dim eqTime As Double = TrueSolarToMeanSolar(tnoon)
    Dim solNoonUTC As Double = 720 + (longitude * 4) - eqTime
    ' min
    Dim newt As Double = JulianCenturies(JulianDayFromJulianCentury(t) - 0.5 + solNoonUTC / 1440.0)

    eqTime = TrueSolarToMeanSolar(newt)
    ' double solarNoonDec = SunDeclination(newt);
    solNoonUTC = 720 + (longitude * 4) - eqTime
    ' min
    Return solNoonUTC
End Function

'***********************************************************************/
'* Name: SunSetUTC  
'* Type: Function   
'* Purpose: calculate the Universal Coordinated Time (UTC) of sunset    
'*   for the given day at the given location on earth   
'* Arguments:   
'* julian : julian day  
'* latitude : latitude of observer in degrees   
'* longitude : longitude of observer in degrees 
'* Return value:    
'* time in minutes from zero Z  
'***********************************************************************/

Public Function SunSetUTC(julian As Double, latitude As Double, longitude As Double) As Double
    Dim t = JulianCenturies(julian)
    Dim eqTime = TrueSolarToMeanSolar(t)
    Dim solarDec = SunDeclination(t)
    Dim hourAngle = SunriseHourAngle(latitude, solarDec)
    hourAngle = -hourAngle
    Dim delta = longitude + Degrees(hourAngle)
    Dim timeUTC = 720 - (4.0 * delta) - eqTime
    ' in minutes
    Return timeUTC
End Function

Public Function SunRiseUTC(julian As Double, latitude As Double, longitude As Double) As Double
    Dim t = JulianCenturies(julian)
    Dim eqTime = TrueSolarToMeanSolar(t)
    Dim solarDec = SunDeclination(t)
    Dim hourAngle = SunriseHourAngle(latitude, solarDec)
    Dim delta = longitude + Degrees(hourAngle)
    Dim timeUTC = 720 - (4.0 * delta) - eqTime
    ' in minutes
    Return timeUTC
End Function

Public Function getTimeString(time As Double, timezone As Integer, julian As Double, dst As Boolean) As String
    Dim timeLocal = time + (timezone * 60.0)
    Dim riseT = JulianCenturies(julian + time / 1440.0)
    timeLocal += (If((dst), 60.0, 0.0))
    Return getTimeString(timeLocal)
End Function

Public Function getDateTime(time As Double, timezone As Integer, [date] As DateTime, dst As Boolean) As System.Nullable(Of DateTime)
    Dim julian As Double = JulianDay([date])
    Dim timeLocal = time + (timezone * 60.0)
    Dim riseT = JulianCenturies(julian + time / 1440.0)
    timeLocal += (If((dst), 60.0, 0.0))
    Return getDateTime(timeLocal, [date])
End Function

Private Function getTimeString(minutes As Double) As String

    Dim output As String = ""

    If (minutes >= 0) AndAlso (minutes < 1440) Then
        Dim floatHour = minutes / 60.0
        Dim hour = Math.Floor(floatHour)
        Dim floatMinute = 60.0 * (floatHour - Math.Floor(floatHour))
        Dim minute = Math.Floor(floatMinute)
        Dim floatSec = 60.0 * (floatMinute - Math.Floor(floatMinute))
        Dim second = Math.Floor(floatSec + 0.5)
        If second > 59 Then
            second = 0
            minute += 1
        End If
        If (second >= 30) Then
            minute += 1
        End If
        If minute > 59 Then
            minute = 0
            hour += 1
        End If
        output = [String].Format("{0:00}:{1:00}", hour, minute)
    Else
        Return "error"
    End If

    Return output
End Function

Private Function getDateTime(minutes As Double, [date] As DateTime) As System.Nullable(Of DateTime)

    Dim retVal As System.Nullable(Of DateTime) = Nothing

    If (minutes >= 0) AndAlso (minutes < 1440) Then
        Dim floatHour = minutes / 60.0
        Dim hour = Math.Floor(floatHour)
        Dim floatMinute = 60.0 * (floatHour - Math.Floor(floatHour))
        Dim minute = Math.Floor(floatMinute)
        Dim floatSec = 60.0 * (floatMinute - Math.Floor(floatMinute))
        Dim second = Math.Floor(floatSec + 0.5)
        If second > 59 Then
            second = 0
            minute += 1
        End If
        If (second >= 30) Then
            minute += 1
        End If
        If minute > 59 Then
            minute = 0
            hour += 1
        End If
        Return New DateTime([date].Year, [date].Month, [date].Day, CInt(hour), CInt(minute), CInt(second))
    Else
        Return retVal
    End If
End Function
End Module

从这个信息开始:

Sunrise_equation

我正在使用它来编写一个仍在制作中的ruby脚本。 我无法理解多部分朱利安日期。

有一件事是清楚的,你应该去准确的太阳运输时间。 然后减去并添加基于纬度和太阳赤纬的semi_diurnal_arc = acos(cos_omega)。 哦! 并确保包括太阳中心和地球折射。 看来这个地球真的是魔术师。

你需要一个公式,其中包括允许地球月球系统围绕太阳的偏心轨道的时间方程。 您需要使用具有适当基准点的坐标,例如WGS84或NAD27等。 您需要使用JULIAN日历而不是我们每天使用的日历来正确地获取这些时间。 在一秒钟内猜测并不容易。 我希望有时间在我的位置,阴影长度等于任何高度。 当太阳在高中午之前和之后高出地平线60度时,每天应该发生两次。 另外,据我所知,你只需要每年添加一天来获得恒星时间,所以如果你想增加你的时钟频率X 366.25 / 365.25你可能现在有一个恒星时钟而不是民用时钟??? “MATH是一个强大的人写了宇宙的语言”

另一个很好的JS实现是suncalc

代码行的数量是可管理的,因此移植到其他语言(C#)当然是可能的。

如果您更喜欢外部服务,可以使用这个漂亮而免费的日出和日落时间API: http//sunrise-sunset.org/api

我一直在将它用于几个项目并且它运行良好,数据似乎非常准确。 只需向http://api.sunrise-sunset.org/json做一个HTTP GET请求

接受的参数:

  • lat:十进制度的纬度。 需要。
  • lng:十进制度经度。 需要。
  • date:YYYY-MM-DD格式的日期。 还接受其他日期格式甚至相对日期格式。 如果不存在,则日期默认为当前日期。 可选的。
  • callback:JSONP响应的回调函数名称。 可选的。
  • 格式化:0或1(默认为1)。 响应时间值将根据ISO 8601表示,day_length将以秒表示。 可选的。

响应包括日出和日落时间以及黄昏时间。

我在UWP中测试了这个nuget包。

https://www.nuget.org/packages/SolarCalculator/

文档有点粗略,在这里:

https://github.com/porrey/Solar-Calculator

你可以用它来获得日出

la =纬度; 和lo =经度; 对于您的地区:

            SolarTimes solarTimes = new SolarTimes(DateTime.Now, la, lo);
            DateTime sr = solarTimes.Sunrise;
            DateTime dt = Convert.ToDateTime(sr);
            textblockb.Text = dt.ToString("h:mm:ss");

您可以使用PM管理器在Visual Studio中安装它

Install-Package SolarCalculator -Version 2.0.2 

或者在“管理NuGet包”Visual Studio库中查找SolarCalculator。

是的,退出了一些。

一些模式链接。

http://williams.best.vwh.net/sunrise_sunset_example.htm

http://www.codeproject.com/Articles/29306/C-Class-for-Calculating-Sunrise-and-Sunset-Times

https://social.msdn.microsoft.com/Forums/vstudio/en-US/a4fad4c3-6d18-41fc-82b7-1f3031349837/get-sunrise-and-sunset-time-based-on-latitude-and-longitude?论坛= csharpgeneral

https://gist.github.com/cstrahan/767532

http://pointofint.blogspot.com/2014/06/sunrise-and-sunset-in-c.html

http://yaddb.blogspot.com/2013/01/how-to-calculate-sunrise-and-sunset.html

https://forums.asp.net/t/1810934.aspx?Sunrise+and+Sunset+timings+Calculation+

http://www.ip2location.com/tutorials/display-sunrise-sunset-time-using-csharp-and-mysql-database

http://en.pudn.com/downloads270/sourcecode/windows/csharp/detail1235934_en.html

http://regator.com/p/25716249/c_class_for_calculating_sunrise_and_sunset_times

http://forums.xkcd.com/viewtopic.php?t=102253

http://www.redrok.com/solar_position_algorithm.pdf

http://sidstation.loudet.org/sunazimuth-en.xhtml

https://sourceforge.net/directory/os:windows/?q=sunrise/set%20times

https://www.nuget.org/packages/SolarCalculator/

http://www.grasshopper3d.com/forum/topics/solar-calculation-plugin

这是我很久以前为Planet Source Code做的一个项目,但幸运的是我把它保存在别处,因为该网站丢失了数据。

https://github.com/DouglasAllen/SunTimes.VSCS.Net

使用此Gist plus

https://gist.github.com/DouglasAllen/c682e4c412a0b9d8f536b014c1766f20

现在简要解释一下这种技术。

首先,您需要真正的太阳能正午或中转站点。

这考虑到了你当地的经度。 它可以通过将其除以15来转换为时间。

那是你从祖鲁区时间或零经度后多少时间。

从中午12:00或中午开始。

并根据经度计算你的时间。

现在困难的部分。 您需要一种方法来计算时间方程。

这是由地球倾斜和围绕太阳的轨道引起的时间差。

这会给你一个想法... https://en.wikipedia.org/wiki/Equation_of_time

但他们有一个更容易的公式.... https://en.wikipedia.org/wiki/Sunrise_equation

这家伙有一些很多人经过或购买的书。 :-D https://en.wikipedia.org/wiki/Jean_Meeus

使用您的平均太阳能运输的第一个计算并计算JDN ... https://en.wikipedia.org/wiki/Julian_day

这被所有角度公式用作朱利安世纪的时间https://en.wikipedia.org/wiki/Julian_year_(astronomy)

https://en.wikipedia.org/wiki/Epoch_(astronomy)

它基本上是你的JDN减去时期,如J2000或2451545.0,除以36525.0,给你朱利安世纪或t,它用于大多数公式,有t作为参数。 有时使用朱利安千年。 在那种情况下,它是3652500.0

诀窍是找到那些帮助你解决时间方程的角度公式。

然后您将获得真正的太阳能运输并减去半天或为您的位置添加半天的阳光。 你会在答案和软件中找到那些。

一旦你得到了一些东西,你可以检查它与搜索时间或在线计算器。

我希望这足以让你前进。 这里到处都是图书馆,但制作自己的图书并不难。 我做了,但它在Ruby中。 它可能证明是有用的.... https://github.com/DouglasAllen/gem-equationoftime

祝好运!

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM