星期一迷你高尔夫7:简化成分测量


12

星期一迷你高尔夫:每周一发布(希望!)一系列简短的挑战赛。
对不起,来晚了;通过写出与之重复的不同想法,我意识到了90%的方法。

我的家人很大,所以我们吃很多食物。我们通常需要加倍,加倍甚至加倍的食谱来制作足够的食物!但是,将测量值相乘可能会很痛苦,因此,有一个程序可以为我们做到这一点很高兴。

挑战

您面临的挑战是创建一个程序或函数,该程序将数字N和字母L作为度量值,并返回相同的度量值,并尽可能简化。这是必需的度量单位(像我的家人一样,都是美国人)及其对应的字母:

1 cup (c) = 16 tablespoons (T) = 48 teaspoons (t)
1 pound (l) = 16 ounces (o)
1 gallon (g) = 4 quarts (q) = 8 pints (p) = 128 fluid ounces (f)

“尽可能简化”是指:

  • 使用最大的测量单位。每个单元的余数可以为1 / 4、1 / 3、1 / 2、2 / 3或3/4。
  • 如有必要,将结果转换为带分数。

例如,4 o四盎司,变成1/4 l四分之一磅。8 t,变成8茶匙2 2/3 T

细节

  • 输入可以采用任何合理的格式;与输出相同。(1 t1,"t"1\nt等)
  • 确保正确处理任何小数部分。(不允许11/4代替1 1/4。)
  • 的数量将总是一个带分数,并总是具有的分母234(或无)。(否1 1/8 T,否1.5 T等)
  • 由于上述原因,不需要向下转换(例如将杯子转换为汤匙)。
  • 该字母将始终是以上(Tcfglopqt)列出的字母之一。

测试用例

这是一个很大的清单,希望涵盖所有类型的案件:

Input   | Output
--------+--------
1/2 t   | 1/2 t
3/4 t   | 1/4 T
1 t     | 1/3 T
1 1/2 t | 1/2 T
2 t     | 2/3 T
2 1/4 t | 3/4 T
2 1/2 t | 2 1/2 t
3 t     | 1 T
10 t    | 3 1/3 T
16 t    | 1/3 c
5 1/3 T | 1/3 c
8 T     | 1/2 c
16 T    | 1 c
36 T    | 2 1/4 c
1/4 c   | 1/4 c
1024 c  | 1024 c
1 o     | 1 o
4 o     | 1/4 l
5 1/3 o | 1/3 l
5 2/3 o | 5 2/3 o
8 o     | 1/2 l
28 o    | 1 3/4 l
28 l    | 28 l
2 f     | 2 f
4 f     | 1/4 p
8 f     | 1/4 q
16 f    | 1/2 q
32 f    | 1/4 g
64 f    | 1/2 g
128 f   | 1 g
2/3 p   | 1/3 q
1 1/3 p | 2/3 q
2 p     | 1/4 g
1 q     | 1/4 g

计分

我们的厨房很小,因此代码应尽可能短,以免使厨房更加狭窄。以字节为单位的最短有效代码获胜;抢七决定进入首先达到其最终字节数的提交。获胜者将在11月9日下周一Monday选。祝您好运!

请注意,此挑战类似于World Big Dosa,但并非重复。



@AlexA。啊,是的,我忘了链接到那个。恕我直言,它足够不同:1)它采用不同的输入格式。2)输出有很大不同。3)需要更多的转换类型。3a)未使用1/8测量。
ETHproductions 2015年

@ETHproductions类似精神等同于重复。
Akangka

9
请原谅,这永远不会发生,请以公制为单位;)
Adriaan

5
您的高尔夫运动越来越少。
丹尼斯

Answers:


2

Mathematica,349 334 330 322字节

这个答案部分感到有些孤独。所以,这是我的尝试。输入应如测试用例中所示。

n=ToExpression@StringSplit@InputString[];i=#~Mod~1&;b=#&@@n;If[Length@n==3,{x,y,z}=n,{x,y,z}=If[IntegerQ@b,{b,0,Last@n},{0,b,Last@n}]];v={0,1/4,1/3,1/2,2/3,3/4};s=<|T->16,t->3,o->16,q->4,p->2,f->16|>;r=<|T->c,t->T,o->l,f->p,p->q,q->g|>;If[v~MemberQ~i[a=(x+y)/s@z],{x,y,z}={Floor@a,i@a,r@z}]~Do~3;Print@Row[{x,y,z}/. 0->""]

说明

首先获取用户输入,在空白处分割输入,然后将其分配给ni=#~Mod~1&创建得到一个数的小数部分,通过服用国防部1.功能b=#&@@n将只是获得的第一个项目n; 那将是一切,直到第一个空间。

如果n长度为3个元素,则意味着我们有一个整数,一个分数一个单位。{x,y,z}=n将分配xyz成为的三个部分n。另一种情况是n长度不超过3个元素;这意味着它将有2个元素长。为了与上面保持一致,我们想x成为整数部分,y成为分数和z单位。因此,在这种情况下,我们需要检查:

  • 如果b(第一元件n)是一个整数,那么x=by=0z=Last@n(的最后一个元素n)。
  • 如果b不是整数,则意味着我们只有一个没有整数的分数。因此,我们要交换xy从上面; 相反,x=0y=b,和z是与上述相同。

现在我们需要设置一些列表:

v = {0, 1/4, 1/3, 1/2, 2/3, 3/4} 如问题中所述,是可接受分数的列表。

s = <|T -> 16, t -> 3, o -> 16, q -> 4, p -> 2, f -> 16|>是一个关联(键值对,如Python中的字典),代表给定单位“增加”到下一个最大单位之一所需的数量。例如,o -> 16是因为在达到1磅之前需要16盎司。

r = <|T -> c, t -> T, o -> l, f -> p, p -> q, q -> g|>是实际上代表下一个单元是什么的关联。例如,T -> c比汤匙大一个单位的杯子就是杯子。

If[v~MemberQ~i[a = (x + y)/s@z], {x, y, z} = {Floor@a, i@a, r@z}]~Do~3

现在,我们最多需要增加3个单位。那将是液体盎司(f)->品脱(p)->夸脱(q)->加仑(g)。因此,现在我们执行以下3次:

  • xy(整数和小数部分)
  • s上面的关联中,获取element z;也就是说,访问当前单位,并在该关联中获取相应的值。
  • 将(x + y)除以上面得到的值,将其分配给a,然后得到其小数部分。
  • 如果那部分在列表中v,那么我们可以增加一个单元;设置xa向下舍入(整数部分),设置y为的小数部分a,然后访问r与当前单位的关联z以获取下一个单位,并将其设置为z
  • 如果它不是的一部分v,而不是,我们没有做任何事情,因为它不能被简化。

完成3次后,我们将输出结果:

Print@Row[{x,y,z}/. 0->””]

这只是{x,y,z}连续打印出来,但是用空字符串替换任何零(如果没有整数或小数),因此不会打印出来。

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.