它是命令词吗?


26

此帖子的灵感来自于“ Puzzling”。注意:下面的拼图是令人窒息的。)

标准电话键盘将字母与数字关联如下:

1 ->
2 -> ABC
3 -> DEF
4 -> GHI
5 -> JKL
6 -> MNO
7 -> PQRS
8 -> TUV
9 -> WXYZ
0 ->

如果在使用上述命令将其转换为按键时,给定的输入单词定义为“有序单词”,则该数量为不递减或不递增。换句话说,结果数不能同时增加减少。

例如,单词CAT翻译为228,它是非递减的,因此是有序单词。但是,单词DOGis 364,它都会增加和减少,因此不是有序单词。

挑战

给定单词,输出是否为有序。

输入项

  • 仅由ASCII字母([A-Z]任何形式)组成的单词(不一定是词典单词)。[a-z]
  • 您选择输入是全部大写还是全部小写,但必须一致。
  • 该单词的长度至少为3个字符。

输出量

输入的单词是有序(真)还是无序(假)的一致真/假值。

规则

  • 完整的程序或功能都是可以接受的。如果是函数,则可以返回输出而不是打印输出。
  • 如果可能,请提供一个在线测试环境的链接,以便其他人可以尝试您的代码!
  • 禁止出现标准漏洞
  • 这是因此所有常见的高​​尔夫规则都适用,并且最短的代码(以字节为单位)获胜。

例子

这是一些有序单词(即真词),还有更多相关的令人困惑的难题。

CAT
TAC
AAA
DEMONS
SKID
LKJONMSRQP
ABCDEFGHIJKLMNOPQRSTUVWXYZ

这是一些非顺序词(即假)

DOG
GOD
ROSE
COFFEE
JKLMNOGHI

相关相关 我不确定这不是骗子,两者之间的唯一变化是abc->t9此挑战是检查单调性吗?
nmjcman101

1
@ nmjcman101是的,这些是相关的,但是除了严格的以外,还有其他(更好的)方法abc->t9
AdmBorkBork '17年

那是有道理的,我确实希望看到某种方法胜过该方法
nmjcman101 '17


测试用例要求:AAA
商业猫

Answers:


13

Python 2中164个 148 132 77字节

-16字节的感谢Rod在其他地方的建议。多亏了阿诺德·帕尔默(Arnold Palmer),frickin'-55个字节。

n=[min(int((ord(i)-58)/3.13),9)for i in input()]
print sorted(n)in[n,n[::-1]]

在线尝试!

输入必须为大写。输出TrueFalse基于其有序性。


说明

第一行将每个字母映射到一个数字。

                               for i in input()   # iterate over the input string
            ord(i)                                # take the ASCII ordinal
                  -58                             # subtract 58
           (         )/3.13                       # divide by 3.13
       int(                )                      # chop off the fractional part
   min(                     ,9)                   # choose the minimum between the number and 9
n=[                                            ]  # assign the resulting list to n

这项工作基于:

          | A   B   C  | D   E   F  | G   H   I  | J   K   L  | M   N   O  | P   Q   R   S  | T   U   V  | W   X   Y   Z
----------+------------+------------+------------+------------+------------+----------------+------------+-----------------
ord(x)    | 65  66  67 | 68  69  70 | 71  72  73 | 74  75  76 | 77  78  79 | 80  81  82  83 | 84  85  86 | 87  88  89  90
----------+------------+------------+------------+------------+------------+----------------+------------+-----------------
x - 58    | 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  32
----------+------------+------------+------------+------------+------------+----------------+------------+-----------------
x ÷ 3.13* | 2.2 2.6 2.9| 3.2 3.5 3.8| 4.2 4.5 4.8| 5.1 5.4 5.8| 6.1 6.4 6.7| 7.0 7.3 7.7 7.9| 8.3 8.6 8.9| 9.3 9.6 9.9 10.2
----------+------------+------------+------------+------------+------------+----------------+------------+-----------------
int(x)    | 2   2   2  | 3   3   3  | 4   4   4  | 5   5   5  | 6   6   6  | 7   7   7   7  | 8   8   8  | 9   9   9   10
----------+------------+------------+------------+------------+------------+----------------+------------+-----------------
min(x, 9) | 2   2   2  | 3   3   3  | 4   4   4  | 5   5   5  | 6   6   6  | 7   7   7   7  | 8   8   8  | 9   9   9   9

*数值为四舍五入。:P

第二行输出数字列表是升序还是降序。

print                                             # print whether...
      sorted(n)                                   # n sorted...
               in[n,n[::-1]]                      # is equivalent to n or n reversed


1
真牛,太棒了。谢谢!
完全人类

我打算将其发布为答案,因为我在每个人都被答案淹没之前就写了它,但您却me住了我:)
Arnold Palmer

8

JavaScript(ES6), 83 ... 71  70字节

返回一个布尔值。

x=>[...x].every(c=>v&=~(k=x,x=parseInt(c,35)*.32|0||10,x<k?2:x>k),v=3)

测试用例


怎么样?

字母转换

我们用于parseInt(c, 35)将输入字符串的每个字母转换为[ 10 .. 34 ]中的某个数字。因为它的基数是35,所以将“ Z”转换为NaN

该表达式* .32 | 0将此数字映射到间隔[ 3 .. 10 ]中,从而导致8个正确的字母组,即“ A”“ Y”。我们需要|| 10获取正确的“ Z”值。

           | A  B  C| D  E  F| G  H  I| J  K  L| M  N  O| P  Q  R  S| T  U  V| W  X  Y   Z
-----------+--------+--------+--------+--------+--------+-----------+--------+------------
parseInt   |10 11 12|13 14 15|16 17 18|19 20 21|22 23 24|25 26 27 28|29 30 31|32 33 34 NaN
-----------+--------+--------+--------+--------+--------+-----------+--------+------------
*.32|0||10 | 3  3  3| 4  4  4| 5  5  5| 6  6  6| 7  7  7| 8  8  8  8| 9  9  9|10 10 10  10

订单测试

我们在位掩码v中跟踪连续数字之间的差异的符号,最初设置为3(0b11):

  • 位#0:当new_value> previous_value时清除
  • 位#1:当new_value <previous_value时清除

先前的值与输入存储在相同的变量x中。这样可以确保第一次迭代(实际上没有先前的值)不会清除任何位,因为仅包含字母的字符串既不大于也不小于任何数字:

('CAT' > 5) === false
('CAT' < 5) === false

除非同时遇到两个符号,否则将对单词进行排序,这将导致v = 0every()失败。


哦,获取每个字母的号码的好方法:)我是否应该借用它感到很痛苦,因为那意味着我会和你打成一片,这似乎不太对劲。
毛茸茸的

6

果冻28,27,25,23,22,21,19, 18个字节

_>
O‘ç82ç88:3IṠḟ0E

在线尝试!

这很有趣!

说明:

                # Define a helper link, decrement a if a > b
_               # Subtract
 >              # Boolean greater than
                # Main link:
O               # The ordinals (ASCII points) of the input
 ‘              # Minus one
  ç82           # Decrement if greater than 82
     ç88        # Decrement if greater than 88
        :3      # Divide each number by 3
          I     # Consecutive differences
           Ṡ    # Sign (-1 if < 0, 0 if == 0, and 1 if > 0)
            ḟ0  # Remove all 0's
              E # All elements are equal?

感谢@ ErikTheOutgolfer,@ leakynun和@BusinessCat节省了所有字节。:)



3

MATL26 25字节

1Y21K250B-Y{c&m8\dZSu|s2<

输入为大写字母。输出为10

在线尝试!

说明

1Y2      % Push 'ABC...XYZ'
1        % Push 1
K        % Push 4
250B     % Push 250 in binary, that is, [1 1 1 1 1 0 1 0]
-        % Subtract (from 4, element-wise): gives [3 3 3 3 3 4 1 4]
Y{       % Convert to cell array, splitting into chunks of those lengths
c        % Convert to char matrix. Gives a 4-column matrix. Chunks of length 3
         % are right-padded with a space
&m       % Implicit input. Push (linear) index of membership in char matrix
8\       % Modulo 8. Converts linear index into 0-based row index
d        % Consecutive differences
ZS       % Sign
u        % Unique
|        % Absolute value
s        % Sum
2<       % Less than 2? Implicit display

字母挑战的适当分数:P
DJMcMayhem

@DJMcMayhem不再了:-D
Luis

3

外壳22 21 19 18字节

±S€Ẋ▲`Ṫo±≤"DGJMPTW

1对于真实输入,0对于虚假输入,返回。输入必须为大写。通过所有测试用例。 在线尝试!

说明

±S€Ẋ▲`Ṫo±≤"DGJMPTW  Implicit input x, e.g. "CAT"
     `Ṫo±≤"DGJMPTW  This part transforms x into a "canonical form" corresponding to the numpad digits
     `Ṫ             Table with flipped arguments
       o±≤          on sign of less-than-or-equal
                    (In Husk, ≤ returns extra information we don't want, so we take sign of the result to get 0 or 1.)
          "DGJMPTW  of this string and x.
                    This gives, for each char in x, a bit array of comparisons with the chars in the string:
                    y = [[0,0,0,0,0,0,0],[0,0,0,0,0,0,0],[1,1,1,1,1,1,0]]
   Ẋ▲               Maxima of adjacent pairs: [[0,0,0,0,0,0,0],[1,1,1,1,1,1,0]]
 S€                 1-based index in y as sublist: 2
±                   Sign: 1

3

Python 2,60个字节

a=[3681/ord(c)for c in input()]
print sorted(a)in[a,a[::-1]]

在线尝试!

接受小写输入。

怎么运行的

⌊3681/ X ⌋从减小

  • 38〜37在X ≈96.8684210526,前a;
  • 37〜36在X ≈99.4864864865,之间cd;
  • 36至35在X ≈102.25,之间fg;
  • 35〜34在X ≈105.171428571,之间ij;
  • 34〜33在X ≈108.264705882,之间lm;
  • 33〜32在X ≈111.545454545,之间op;
  • 32〜31在X ≈115.03125,之间st;
  • 31〜30在X ≈118.741935484,之间vw;
  • 在30至29 X ≈122.7,后z

2

C ++,375个 199 195 194字节

感谢Shaggy的JavaScript答案:
-5字节,感谢Zacharý

#include<string>
int o(std::string a){std::string m="22233344455566677778889999";for(auto&b:a)b=m[b-65];int j=1,i=0,d=0;for(;j<a.size();++j){if(a[j]>a[j-1])++i;if(a[j]<a[j-1])++d;}return!(i*d);}

int j=1,i=0,d=0可以将for循环到吗?
扎卡里

@Zacharý由于id都在循环块之外使用,所以我不能
HatsuPointerKun

i==0||d==0==> i*d==0
扎卡里

!(i*d)工作吗?(除去后的空间return
扎卡里

@Zacharý是的,它有效
HatsuPointerKun

1

05AB1E,30个字节

A3 8×Ƶ0+S£¹δåā>‚øε`*}.«+¥0K0‹Ë

在线尝试!

-1感谢Magic Octopus Urn


您使用¥0K0.SË是因为¥0‹Ë不正确吗?我不知道是否0.S需要。
魔术章鱼缸

@MagicOctopusUrn实际上¥0K0‹Ë似乎可以工作。
暴民埃里克(Erik the Outgolfer)'17年

是的,如果要删除0,应该删除;在我的回答中,我不确定它是否有效。
魔术章鱼缸

@MagicOctopusUrn我要删除0,因为否则会出现假阴性。您的答案可能会有所不同。
暴民埃里克'17

1

视网膜,65字节

T`_ADGJMPTW`d
}T`L`_L
(.)\1*
$1$*1<
(1+)<(?!\1)
$1>
1

^(<*|>*)>$

在线尝试!链接包括测试用例。说明:

T`_ADGJMPTW`d

将每个键上的第一个字母更改为数字。(这是1的偏移量,但对于升/降支票并不重要。另一方面,零会使我的生活更加困难,所以我留了一个填充字符。)

}T`L`_L

将其余所有字母随机洗净1,然后重复直到将它们全部转换为数字为止。

(.)\1*
$1$*1<

将数字转换为一进制,但每次运行相同数字仅一次。一元值用<... 分隔

(1+)<(?!\1)
$1>

...但是,如果LHS大于RHS,则将校正<>

1

删除1不再需要的。

^(<*|>*)>$

检查单词是否正确。(尾随>来自最后一个数字,该数字总是比后面的空白大)。


太酷了。感谢您的详尽解释。
AdmBorkBork

1

Pyth,23个字节

我最重要的Pyth答案之一!感谢@LeakyNun,节省了6个字节。最初的解决方案如下。

/{_BKmhS,9/a58Cd3.13zSK

测试套件。

Pyth,29个字节

KmhS+9]/-Cd58 3.13w|qKSKqK_SK

测试套件。


说明

/{_BKmhS,9/a58Cd3.13zSKQ-Q表示已评估的输入,并在末尾隐含

 {-重复数据删除
  _-倒车
   B-分叉,创建两个元素的列表,[B,A(B)]
    K-具有自动分配功能的变量:
     mz-映射输入:
      hS-最小值(排序列表的第一个元素)
        ,-用以下元素创建一个包含两个元素的列表[A,B]:
         9-数字文字9
          //-的整数除法:
           a58Cd-58和ord(current_element)之间的绝对差   
                3.13-数字文字3.13
                    SK-K排序
/ Q-计算[K,K [::-1]]中输入的出现                


1

05AB1E21 17字节

A•22ā₂•Sās×J‡Ô¥dË

使用05AB1E编码。

在线尝试!验证所有测试用例!

说明

A                   # Push the lowercase alphabet
 •22ā₂•             # Push the number 33333434
       S            # Split into an array
        ā           # Get the range of indices [1 .. length]
         s×         # Swap and string multiply
           J        # Join that array
            ‡       # Transliterate

现在,这实际上将以下字母映射到以下数字:

abcdefghijklmnopqrstuvwxyz
↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓
11122233344455566667778888

             Ô      # Remove consecutive duplicates
              ¥     # Compute the delta's of the list
               d    # Check if the number is greater or equal to 0
                Ë   # Check if all elements are the same

1

JavaScript(ES6),107 97 95 92 88 85字节

适用于大小写混合的字符串。返回1真还是0假。

s=>(s=(a=[...s].map(c=>(parseInt(c,36)-3)/3.13%10|0||9))+"")==a.sort()|s==a.reverse()
  • 多亏Rod,节省了10个字节。

试试吧

o.innerText=(f=
s=>(s=(a=[...s].map(c=>(parseInt(c,36)-3)/3.13%10|0||9))+"")==a.sort()|s==a.reverse()
)(i.value="Cat")
oninput=_=>o.innerText=f(i.value)
<input id=i><pre id=o>


1
Math.min((parseInt(c,36)-3)/3.13|0,9)而是"2..9"[parseInt(c,36)-10]节省一些字节
Rod

谢谢@Rod; 非常好。我必须将其归档以备将来使用。
毛茸茸的


谢谢@ThePirateBay,但不幸的是,该输入失败了AAA
毛茸茸的

1

盖亚(Gaia)29 27 25 17 字节

ċ⟨):“QX’>¦Σ⁻3/⟩¦o

在线尝试!

说明

ċ                  Turn the input into a list of code points
 ⟨            ⟩¦   Map this block to each code point:
  )                 Increment it
   :                Copy it
    “QX’            Push [81 88]
        >¦          Check if the code point is greater than each of [81 88]
          Σ         Sum the results
           ⁻        Subtract from the code point
            3/      Integer divide the result by 3
                o  Check if the resulting list is in sorted order (increasing or decreasing)

1

05AB1E,13个字节

ÇÍžq÷8
7:Ô¥dË

每当我看到小键盘问题时,都必须做出基于pi的答案。

在线尝试验证所有测试用例

Ç                    # ASCII code of each letter in the input
 Í                   # add 2
  žq÷                # divide by pi
     8 7:            # replace 8 with 7
         Ô           # remove duplicates
          ¥          # deltas
           d         # each >= 0 ?
            Ë        # are all elements equal?


0

C#(.NET Core),133字节

using System.Linq;q=>{var u=q.Select(c=>(int)((c-58)/3.13));var z=u.Zip(u.Skip(1),(a,b)=>a-b);return!(z.Any(d=>d<0)&z.Any(d=>d>0));};

在线尝试!

我觉得这里还有一些节省的空间,但是C#不是一种简洁的语言,所以也许没有。取消高尔夫:

bool Ordered(string word){

    IEnumerable<int> keys = word.Select(character => (int)((character - 58)/3.13)); 
    // convert characters to keypad number

    IEnumerable<int> differences = keys.Zip(keys.Skip(1), (a, b)=> a-b); 
    // difference between consecutive elements

    return !(differences.Any(diff => diff<0) & differences.Any(diff => diff>0)); 
    // false if both positive and negative differences exist
}

特别是,我认为有一种表达最终检查有效性的较短方法,可能是一种将其内联的方法Zip。寻找一种Zip无需临时存储即可表达的方法Skip也可以节省一些时间,但是我怀疑这样做是否更简洁。


0

Python 3中143个 147 148 149 130字节

def g(s,f=lambda c:min(int((ord(c)-58)/3.13),9)):x=[f(a)-f(b)for a,b in zip(s,s[1:])];return any(t<0for t in x)*any(t>0for t in x)

现在最好的办法。粗略功能根据ASCII码将字母转换为数字。肯定会有一些改进。0是真实的,1是虚假的(抱歉)。Rod节省了10个字节,Xcoder先生又节省了3个字节。

在线尝试!


您可以x=[f(a)-f(b)for a,b in zip(s,s[1:])]用来保存一些字节
Rod

同时,min(int((ord(c)-58)/3.13),9)是为char转换较短的方式
罗德


@Rod谢谢!很有帮助。
C McAvoy

您需要四处交换输出,以使其生效。
毛茸茸的

0

Python 2中111个 103字节

-8字节感谢@Arnold帕尔默:没有lower()必要

  • 以大写字母作为输入。
lambda x:sorted(f(x))in[f(x),f(x)[::-1]]
f=lambda x:['22233344455566677778889999'[ord(i)-65]for i in x]

在线尝试!


1
您可以删除,.lower()因为无论您指定哪种输入都可以。
阿诺德·帕尔默

0

PHP 7,98 + 1 95 + 1 84 + 1字节

阿尔诺尔德答案高尔夫球场

for(;$c=ord($argn[$i]);$v|=$i++?$p>$k?2:$p<$k:0,$p=$k)$k=($c-58)*.32%10?:9;echo$v<3;

接受大写;空输出,虚假,1真实。

与管道一起运行-nR在线尝试

原始帖子:

for(;$c=$argn[$i++];$p?$a[]=$p<=>$k:0,$p=$k)$k=(ord($c)-58)/3.13-($c>Y)|0;echo min($a)*max($a)>=0;

0

CJam,37 31 30 27字节

q{_"SVZY"#g-i3/}%_$_W%](e=g

在线尝试

当然,丑陋的版本最终会变短。

q{        e# For each character in string...
_"SVZY"#g e# Get index of that character in "SVZY". Signum that. (returns 1 or 0 if inside string, -1 if not.)
-i3/      e# Subtract value from character (i.e 'Z' becomes 'Y', 'F' becomes 'G'). Convert to int. Integer divide by 3. (this is just how the math works out for proper mapping of characters to phone digits.)
}%
_$_W%]    e# Put mapped string, sorted version, and reverse sorted version in array.
(         e# Pop mapped string from array onto stack.
e=        e# Count occurences of mapped string in array.
g         e# Signum.

0

C(gcc)183169153117字节

#define a(b)(int)fmin(*(b c)/3.2,27)
d(char*c){int r=1,p=1;for(;1<strlen(c);)r&=a()<=a(1+),p&=a()>=a(++);return r|p;}

在线尝试!

旧解决方案:

#define a(b)(int)((int)(b*.32-17.6)*.9)
d(char*c){int l=~-strlen(c),i=0,r=1,p=1;for(;i<l;++i)r&=a(c[i])<=a(c[i+1]),p&=a(c[l-i])<=a(c[l-i-1]);return r+p;}

感谢ThePirateBay,节省了8个字节。

旧的旧解决方案:

d(char*c){char*a="22233344455566677778889999";int l=strlen(c)-1,i=0,r=1,p=1;for(;i<l;++i){if(a[c[i]-65]>a[c[i+1]-65])r=0;if(a[c[l-i]-65]>a[c[l-i-1]-65])p=0;}return r+p;}

老老老解决办法:

d(char*c){char*a="22233344455566677778889999";int l=strlen(c);int i,r=1,p=1;for(;i<l-1;++i)if(a[c[i]-65]>a[c[i+1]-65])r=0;for(i=l-1;i>0;--i)if(a[c[i]-65]>a[c[i-1]-65])p=0;return r+p;}

0

TI-Basic,92 66字节

ΔList(int(seq(inString("BC DEF GHI JKL MNO PQRSTUV WXYZ",sub(Ans,I,1))/4,I,1,length(Ans
0≤min(Ansmax(Ans

将字符串中的每个字符转换为0到7之间的整数,并取每个连续元素之间的差;然后检查最小和最大差异是否具有相同的符号(或均为0)。


我认为ΔList(int(4^-1seq(inString("DEF GHI JKL MNO PQRSTUV WXYZ",sub(Ans,I,1))+3,I,1,length(Ans可以节省一个字节。
lirtosiast

0

Zsh73 69 57字节

使用@ anders-kaseorg的3681/code转换为-12个字节

for c (${(s::)1})((y=3681/#c,A|=y<p,D|=p&&p<y,p=y,!D|!A))

在线尝试! 在线尝试! 在线尝试!

我们滥用的几件事:

  • ((statement,statement,...))是一个算术表达式序列,如果最后一条语句为非零,则返回真值。
  • 循环的返回值是循环中最后一条语句的返回值。
  • 算术运算符优先级对我们来说很好,因为只使用了一对 不带括号的。如果!绑定范围小于,则可以节省一个字节&
  • 未设置的参数0在算术扩展中扩展为。
  • 我们用来映射到键盘编号的功能是CODE / 3.2 - 18(具有的一种特殊情况Z),但是由于我们只需要在代码之间进行更改,因此我们无需进行线性调整。
for c (${(s::)1})           # split into characters
    (( y = #c-90 ? 0^(#c/3.2) : 27,   # this sets y to the keypad number + 18
       A |= y < p,          # set the A flag if we detect it is not ascending
       D |= p && p < y,     # ditto descending, don't compare on first iteration
       p = y,               # save the current character
       !D | !A              # return false if D and A are both set
    ))

如果可以交换真/假值,则可以节省2个字节。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.