【问题标题】:Converting wind direction in angles to text words将角度的风向转换为文本单词
【发布时间】:2011-11-21 09:12:54
【问题描述】:

我有来自风向标的风向数据,数据以 0 到 359 度表示。

我想把它转换成文本格式(罗盘玫瑰),有 16 个不同的方向。

基本上我想知道是否有一种快速巧妙的方法可以将角度读数缩放到 16 个字符串数组以打印出正确的风向,而无需使用一堆 if 语句并检查角度范围

风向可查here

谢谢!

【问题讨论】:

  • 正在寻找 N、NNW、NW、WNW 等音调的文本?
  • 问题中的链接现已损坏
  • 如果您正在寻找相反的转换(罗盘方向到数字度数),这是一个答案:stackoverflow.com/questions/42597344/…

标签: angle


【解决方案1】:

编辑:

由于每 22.5 度就有一个角度变化,所以方向应该在 11.25 度后换手。

因此:

349-360//0-11 = N
12-33 = NNE
34-56 = NE

使用 327-348 的值(整个 NNW 频谱)未能为 eudoxos 的答案产生结果。 经过一番思考,我找不到他的逻辑缺陷,所以我重写了自己的..

def degToCompass(num):
    val=int((num/22.5)+.5)
    arr=["N","NNE","NE","ENE","E","ESE", "SE", "SSE","S","SSW","SW","WSW","W","WNW","NW","NNW"]
    print arr[(val % 16)]

>>> degToCompass(0)
N
>>> degToCompass(180)
S
>>> degToCompass(720)
N
>>> degToCompass(11)
N
>>> 12
12
>>> degToCompass(12)
NNE
>>> degToCompass(33)
NNE
>>> degToCompass(34)
NE

步骤:

  1. 将角度除以 22.5,因为 360 度/16 个方向 = 22.5 度/方向变化。
  2. 添加 .5 以便在截断值时可以打破更改阈值之间的“平局”。
  3. 使用整数除法截断值(因此没有四舍五入)。
  4. 直接索引到数组并打印值(mod 16)。

【讨论】:

  • 这里为什么要减1?对于 0 度的事件,这似乎给你 -1,给你一个索引越界错误。除此之外,正是我的想法。
  • 去掉减1并输入值359。IndexOutOfBounds错误。我做了一个减 1 并遗漏了一个小检查。如果
【解决方案2】:

这是 steve-gregory 答案的 javascript 实现,对我有用。

function degToCompass(num) {
    var val = Math.floor((num / 22.5) + 0.5);
    var arr = ["N", "NNE", "NE", "ENE", "E", "ESE", "SE", "SSE", "S", "SSW", "SW", "WSW", "W", "WNW", "NW", "NNW"];
    return arr[(val % 16)];
}

请参阅his answer 了解有关逻辑的说明。

【讨论】:

  • Math.floor(n + 0.5)Math.round(n) 有什么不同?它的性能更高吗?
  • 这不是出于性能原因...也许Math.round(n) 可以正常工作。单元测试值得一试。
  • 哈哈,我写了这个然后发到这里,看到了你的,我个人会把 %16 移到第一个计算中..
【解决方案3】:

注意四舍五入,349...11 之间的角度应为“N”,因此先添加半个扇区 (+(360/16)/2),然后将 360 上的溢出处理 %360,然后除以 360 /16:

["N","NNW",...,"NNE"][((d+(360/16)/2)%360)/(360/16)]

【讨论】:

  • 显然没有一个同事发帖 :-( [他们的答案都应该是 F,sice 359 应该很明显是 N,但他们会得到 NNE 之类的。]
  • @eudoxos:最后的除数应该是 360/16 。更正了上面的答案。现在工作。不过,在大多数语言中,您可能需要 Math.floor 或类似的东西。
  • 谢谢@DoubleMalt,如果有人在 359 获得 N 和在 1 获得 NNE,请使用 [Math.floor(((d+(360/16)/2)%360)/(360/16))]
  • 当心你是否在 Python 2 中使用它。这让我很困惑,为什么它不能正常工作。这是使用整数除法,并且需要每个除法的至少一侧是浮点数才能工作。将 (360/16) 的两个实例替换为 (360.0/16) 将使其正常工作。
【解决方案4】:

此 JavaScript 适用于只需要 8 个基本方向并想要相应箭头的任何人。

function getCardinalDirection(angle) {
    const directions = ['↑ N', '↗ NE', '→ E', '↘ SE', '↓ S', '↙ SW', '← W', '↖ NW'];
    return directions[Math.round(angle / 45) % 8];
}

【讨论】:

    【解决方案5】:

    我检查了这个,它工作得很好,而且看起来很准确。 来源:http://www.themethodology.net/2013/12/how-to-convert-degrees-to-cardinal.html 阿德里安·史蒂文斯

        public static string DegreesToCardinal(double degrees)
        {
            string[] caridnals = { "N", "NE", "E", "SE", "S", "SW", "W", "NW", "N" };
            return caridnals[(int)Math.Round(((double)degrees % 360) / 45)];
        }
    
        public static string DegreesToCardinalDetailed(double degrees)
        {
            degrees *= 10;
    
            string[] caridnals = { "N", "NNE", "NE", "ENE", "E", "ESE", "SE", "SSE", "S", "SSW", "SW", "WSW", "W", "WNW", "NW", "NNW", "N" };
            return caridnals[(int)Math.Round(((double)degrees % 3600) / 225)];
        }
    

    【讨论】:

      【解决方案6】:

      我认为这样做更容易:

      1. 将方向移动 11.25
      2. 在方向列表末尾添加一个“N”来处理'over 360',

      DirTable = ["N","NNE","NE","ENE","E","ESE", "SE","SSE","S","SSW","SW","WSW", "W","WNW","NW","NNW",**"N"**]; 
      
      wind_direction= DirTable[Math.floor((d+11.25)/22.5)];
      

      【讨论】:

        【解决方案7】:

        如果您来到这里并且只想将您的学位分为 8 个方向之一。

        function degToCompass(num){
            const val =  Math.floor((num / 45) + 0.5);
            const arr = ["N","NE","E", "SE","S","SW","W","NW"];
            return arr[(val % 8)]
        

        【讨论】:

          【解决方案8】:

          我可能只是做简单的度数划分来获得数组中的位置或枚举值或可以为您提供所需文本的东西。只需四舍五入你的所有部门。 360/16 = 22.5,因此您需要除以 22.5 来获得位置。

          字符串[] a = [N,NNW,NW,WNW,...,NNE]

          【讨论】:

            【解决方案9】:

            这很好用

            #!/usr/bin/env python
            
            def wind_deg_to_str1(deg):
                    if   deg >=  11.25 and deg <  33.75: return 'NNE'
                    elif deg >=  33.75 and deg <  56.25: return 'NE'
                    elif deg >=  56.25 and deg <  78.75: return 'ENE'
                    elif deg >=  78.75 and deg < 101.25: return 'E'
                    elif deg >= 101.25 and deg < 123.75: return 'ESE'
                    elif deg >= 123.75 and deg < 146.25: return 'SE'
                    elif deg >= 146.25 and deg < 168.75: return 'SSE'
                    elif deg >= 168.75 and deg < 191.25: return 'S'
                    elif deg >= 191.25 and deg < 213.75: return 'SSW'
                    elif deg >= 213.75 and deg < 236.25: return 'SW'
                    elif deg >= 236.25 and deg < 258.75: return 'WSW'
                    elif deg >= 258.75 and deg < 281.25: return 'W'
                    elif deg >= 281.25 and deg < 303.75: return 'WNW'
                    elif deg >= 303.75 and deg < 326.25: return 'NW'
                    elif deg >= 326.25 and deg < 348.75: return 'NNW'
                    else: return 'N'
            
            def wind_deg_to_str2(deg):
                    arr = ['NNE', 'NE', 'ENE', 'E', 'ESE', 'SE', 'SSE', 'S', 'SSW', 'SW', 'WSW', 'W', 'WNW', 'NW', 'NNW', 'N']
                    return arr[int(abs((deg - 11.25) % 360)/ 22.5)]
            
            i = 0
            while i < 360:
                    s1 = wind_deg_to_str1(i)
                    s2 = wind_deg_to_str2(i)
                    print '%5.1f deg -> func1(%-3s), func2(%-3s), same:%s' % (i, s1, s2, ('ok' if s1 == s2 else 'different'))
                    i += 0.5
            

            【讨论】:

              【解决方案10】:

              进行反向转换(罗盘字母缩写为度数):

              function getDir($b)
              {
              
                 $dirs = array('N'=>0, 'NNE'=>22.5,"NE"=>45,"ENE"=>67.5, 'E'=>90,'ESE'=>112.5, 'SE'=>135,'SSE'=>157.5, 'S'=>180,'SSW'=>202.5, 'SW'=>225,'WSW'=>247.5, 'W'=>270,'WNW'=>292.5,'NW'=>315,'NNW'=>337.5, 'N'=>0,'North'=>0,'East'=>90,'West'=>270,'South'=>180);
                 return $dirs[$b];
              }
              

              【讨论】:

              • 这不能回答问题。
              【解决方案11】:

              Javascript 函数 100% 工作

              function degToCompass(num) { 
                  while( num < 0 ) num += 360 ;
                  while( num >= 360 ) num -= 360 ; 
                  val= Math.round( (num -11.25 ) / 22.5 ) ;
                  arr=["N","NNE","NE","ENE","E","ESE", "SE", 
                        "SSE","S","SSW","SW","WSW","W","WNW","NW","NNW"] ;
                  return arr[ Math.abs(val) ] ;
              }
              

              步骤

              1. 给定一个 360 度角
              2. 由于北在 -11.25 到 11.25 之间,我们减去 11.25 以获得准确度
              3. 将角度除以 22.5,因为 360 度/16 个方向 = 22.5 度/方向变化
              4. Math.abs 为负数仍为北
              5. 从 arr from answer 中选择片段

              希望对你有帮助

              【讨论】:

              • 它不起作用。 degToCompass(70) 返回 NNE,正确答案是 ENE。 climate.umn.edu/snow_fence/components/…
              • 需要更多测试! -90 应该是西而不是东,12 度应该是第一个远离北方的过渡。
              • @SamMason 该函数的创建适用于 0 到 360 之间的角度。我已修改为现在可以使用任何角度 感谢您的输入
              【解决方案12】:

              这是一个单行的python函数:

              def deg_to_text(deg):
                  return ["N","NNE","NE","ENE","E","ESE", "SE", "SSE","S","SSW","SW","WSW","W","WNW","NW","NNW"][round(deg/22.5)%16]
              

              显然它可以分成多行以提高可读性/pep8

              【讨论】:

                【解决方案13】:

                在 Excel 中使用: VLOOKUP(MROUND(N12,22.5),N14:O29,2,FALSE)

                单元格 N12 是指向需要答案的度数的方向。 范围 N14:O29 正在查找扇区(A 到 R):

                风部门 0个 22.5 乙 45℃ 67.5 天 90 东 112.5 楼 135克 157.5小时 180 焦 202.5 千 225 升 247.5 百万 270牛 292.5 页 315问 337.5 转

                【讨论】:

                  【解决方案14】:

                  我大量使用 R,需要一个解决方案。这是我想出的,并且适用于我喂过的所有可能的组合:

                  degToCardinal <- function(degrees) {
                    val <- as.integer((degrees / 22.5) + 0.5)
                    arr <- c("N","NNE","NE","ENE","E","ESE", "SE", "SSE","S","SSW","SW","WSW","W","WNW","NW","NNW")
                    return(arr[((val+1) %% 16)])
                  }
                  

                  【讨论】:

                    【解决方案15】:

                    想使用@eudoxos,但需要将所有部分组合在一起:

                    def deg_to_compass(d):
                      return ["N", "NNE", "NE", "ENE", "E", "ESE", "SE", "SSE",
                            "S", "SSW", "SW", "WSW", "W", "WNW", "NW", "NNW"] [math.floor(((d+(360/16)/2)%360)/(360/16))]
                    

                    借@Hristo markow查看结果:

                    for i in range(0,360):
                      print (i,deg_to_compass(i) == wind_deg_to_str2(i))
                    

                    【讨论】:

                      【解决方案16】:
                      compass_direction =["NNE","NE","ENE","E","ESE","SE","SSE","S","SSW","SW","WSW","W","WNW","NW","NNW","N"]
                      
                      for i in range (0,365):
                          index = (int) ((((i / 11.25) - 1) /2) % 16) 
                          print(f"Angle: {i:3}, Index: {index}, Compass: {compass_direction[index]}")
                      

                      【讨论】:

                        猜你喜欢
                        • 1970-01-01
                        • 2019-11-18
                        • 1970-01-01
                        • 1970-01-01
                        • 1970-01-01
                        • 1970-01-01
                        • 1970-01-01
                        • 1970-01-01
                        • 1970-01-01
                        相关资源
                        最近更新 更多