Frações intermediárias

13

Frações intermediárias

O desafio:

Você precisará criar um código que leve pelo menos três entradas; 2 números inteiros e "uma representação de fração" - qualquer que seja o tipo que se adequa ao seu idioma para representar os incrementos de fração), ie. Se você escolher uma string, a entrada será "1/4" ou você poderá escolher 2 entradas inteiras extras ou uma tupla ou w / e.

A entrada pode ser razoável em qualquer lugar (STDIN, argumentos de função, de um arquivo, etc.), assim como a saída (STDOUT, valor de retorno da função para um arquivo, etc.)

Regras:

  1. A "fração" de entrada sempre será uma fração válida, menor que 1; exemplo "1/4"
  2. O segundo número inteiro de entrada sempre terá um valor mais alto que o primeiro número inteiro. Ou seja, o primeiro número inteiro de entrada sempre terá um valor menor que o segundo.
  3. Os números inteiros de entrada podem ser negativos.
  4. As frações produzidas devem ser reduzidas o máximo possível (simplificado)

O código precisará gerar cada "passo de fração" entre os 2 números em incrementos da fração de entrada.

O código deve ser um programa ou função, conforme indicado aqui

Exemplo 1:

Entrada: -2,3,"1/2"

Resultado:

 -2
 -3/2 
 -1 
 -1/2 
  0 
  1/2 
  1 
  3/2  
  2 
  5/2 
  3

Exemplo 2:

Entrada: 1,2,"2/3"

Resultado:

1
5/3
2

ou

1
4/3
2

Nota: A contagem pode começar em qualquer direção (obrigado @Mego)

Isso é , então a resposta mais curta em bytes vence.

Alex Carlsen
fonte
A fração poderia ser tomada como 2 entradas inteiras, perfazendo 4 entradas totais?
Mego
Acho doente manter a restrição de máximo de 3 entradas - Gostaria de ver o código para 4 entradas aswell
Alex Carlsen
Nesse caso, que tal ter uma lista / tupla / matriz / algum outro tipo iterável contendo dois números inteiros para a terceira entrada? Isso não é fundamentalmente diferente de 4 entradas inteiras. Você também deve esclarecer que a fração não será igual a 0.
Mego 15/04
@Mego Depois de pensar nisso, não vejo por que não deveria ser permitido alterado para "código que leva pelo menos 3 entradas"
Alex Carlsen
1
@beaker enquanto a saída está correta ea entrada vem de pelo menos 2 números inteiros, o resto é com você :) - Eu mantive a parte de entrada muito extremidade aberta, para ver respostas diferentes
Alex Carlsen

Respostas:

5

Oitava, 34 30 bytes

@(a,b,c)rats(union([a:c:b],b))

Agora leva a fração como uma expressão numérica em vez de numerador e denominador separados.

Amostra em ideone

taça
fonte
1
Então, por que você não pode usar @(a,b,c)rats(union([a:c:b],b))?
Luis Mendo
@LuisMendo Eu posso, se expressões matemáticas são entradas aceitáveis ​​(o resultado efetivo de 1/2uma entrada numérica em vez de string), mas não é assim que eu interpreto "uma representação de fração". Se o OP concordar, ficarei feliz em cortar 4 bytes.
224166
Ah eu vejo. Bem, estou usando isso na minha resposta do Matlab. O mesmo acontece com a resposta Mathematica, aparentemente, a menos que "número racional" é um tipo de dado específico
Luis Mendo
@beaker, eu realmente respondi #
Alex Carlsen
@VisualBean Código já atualizado.
proveta de
11

Mathematica, 16 bytes

Range@##⋃{#2}&

Uma função sem nome que pega dois números inteiros e um número racional e retorna uma lista de números, por exemplo:

Range@##⋃{#2}&[-2, 3, 1/2]
(* {-2, -(3/2), -1, -(1/2), 0, 1/2, 1, 3/2, 2, 5/2, 3} *)

O Mathematica Rangefaz exatamente o que o desafio pede, exceto que omite o limite superior se a diferença entre o limite inferior e o superior não for exatamente um múltiplo do tamanho da etapa. Portanto, pegamos o Union(usando ) com a lista que contém apenas o limite superior, o que garante que ele apareça exatamente uma vez. Observe que Unionclassificará o resultado, mas queremos que seja classificado de qualquer maneira, pois o tamanho da etapa é sempre positivo. Além disso, como estamos trabalhando com argumentos, eles são automaticamente reduzidos o máximo possível.

Martin Ender
fonte
10

T-SQL 2012+, 831 535 477 270 246 240 219 bytes

Observe que este é um liner - o sql não possui função de compilação para reduzir a fração. Pode não ser o melhor idioma para esse tipo de pergunta. É legível por humanos (mais ou menos - em comparação com alguns dos outros idiomas).

DECLARE @f INT=-5,@t INT=3,@n INT=3,@ INT=8;

WITH C as(SELECT
top((@t*@-@f*@)/@n+1)ROW_NUMBER()OVER(ORDER BY @)M
FROM sys.messages)SELECT(SELECT
IIF(V%@=0,LEFT(V/@,9),CONCAT(V/MAX(M),'/',ABS(@)/MAX(M)))FROM c
WHERE V%M=0AND @%M=0)FROM(SELECT
@f*@+@n*~-M V FROM c)k

Experimente online

t-clausen.dk
fonte
A linguagem não é chamada T-SQL e não "Sqlserver"?
David Conrad
1
@DavidConrad, a linguagem é TSQL, mas existem versões diferentes do sqlserver, e o TSQL funcionará no sqlserver 2012 por causa da palavra-chave IIF. Qual usaria a palavra-chave CASE em versões mais antigas. Adicionada sua sugestão
t-clausen.dk 15/04
Bom trabalho. Você pode economizar alguns alterando @nou @dpara simples @. Sua consulta CTE para N poderia ser N AS(SELECT N FROM(VALUES(1),(1),(1),(1),(1),(1),(1),(1),(1),(1))M(N))ou N AS(SELECT 1N FROM sys.all_views). Dado que é quase garantido que haja algumas centenas nessa visualização, você também pode reduzir as junções cruzadas. ISNULLé menor do que COALESCEe deve funcionar
MickyT
@MickyT graças a suas sugestões e alguns de meu próprio, eu consegui reduzir o comprimento de 296 bytes,
t-clausen.dk
Grande trabalho lá
MickyT
6

Python 2, 81 bytes

from fractions import*
a,b,c=map(Fraction,input())
while a<b:print a;a+=c
print b

Experimente online

Mego
fonte
5

Haskell, 31 26 bytes

f a b c=min[b]$a:f(a+c)b c

Avaliação preguiçosa FTW! Demo:

*Main> import Data.Ratio
*Main Data.Ratio> f (-2) 3 (1%2)
[(-2) % 1,(-3) % 2,(-1) % 1,(-1) % 2,0 % 1,1 % 2,1 % 1,3 % 2,2 % 1,5 % 2,3 % 1]
*Main Data.Ratio> f 1 2 (2%3)
[1 % 1,5 % 3,2 % 1]

(Fui inicialmente tentado pela [a,a+c..b]notação de Haskell , mas ela tem algumas peculiaridades que exigem algo como f a b c|l<-[a,a+c..b-c/2]=l++[b|last l<b]41 bytes ou f a b c=[x|x<-[a,a+c..],x<b]++[b]33.)

Anders Kaseorg
fonte
Eu gosto da sua solução! No entanto, acho que você precisa incluir import Data.Rationa sua contagem de bytes também, acho que você não pode usar fsem isso, certo?
flawr
2
@ flawr: caso agradável da borda: você não precisa Data.Ratiopor fsi só, porque é polimórfico para todos os tipos numéricos. No entanto, quando você quiser chamá-lo com valores do tipo Ratio, precisará da importação. O desafio requer apenas "criar código que ...", não usá-lo. Eu acho que está tudo bem sem a importação.
N /
1
Mais precisamente, você só precisa da importação para o %operador criar as frações de teste 1 % 2e 2 % 3. Não estou trapaceando aqui: você pode realmente colocar esses 26 bytes em um arquivo sozinho, executar o intérprete nesse módulo e ter a interação que eu exibi. (Você pode até mesmo evitar a digitação import Data.Rationa interação demo, se você em vez soletrar %como Data.Ratio.%.)
Anders Kaseorg
5

MATL , 16 15 bytes

3$:3Gvu9X10ZGZD

Isso pode falhar para denominadores muito grandes. Espero que o formato de saída seja aceitável.

Experimente online!

3$:    % take three inputs and generate range
3G     % push third input again
v      % vertically concatenate. Gives vertical array as output 
u      % get unique elements (i.e. remove the last one if it is repeated)
9X1    % predefined literal 'rat'
0ZG    % set rational format
ZD     % display using that format
Luis Mendo
fonte
5

Ruby , 32 54 48 bytes

->a,b,c{(a..b).step(c){|x|p x%1>0?x:x.to_i};p b}

Essa solução é baseada na resposta Python do Mego e assume que csempre será um Rationalformato de fração de Ruby. Experimente online!

Editar: Corrigido um erro em que números inteiros não eram apresentados como números inteiros. -6 bytes graças a Not That Charles e MegaTom.

As funções são chamadas desta maneira:

> f=->a,b,c{(a..b).step(c){|x|p x%1>0?x:x.to_i};p b}
> f[1,4,Rational(2,3)]
1
(5/3)
(7/3)
3
(11/3)
4
Sherlock9
fonte
(3/1) não deve ser simplesmente 3?
Edc65
A mais simples Rationalforma de 3em Ruby é(3/1)
Sherlock9
.step(b,c).mapdeve reduzir a contagem de bytes aqui
Não que Charles
(a==a.to_i)pode ser a%1==0de -4 bytes.
MegaTom 22/06/19
-2,3,1/2r(exemplo 1) imprime o último 3duas vezes.
Value Ink
3

Julia, 14 bytes

f(a,b,c)=a:c:b

Isso é semelhante à resposta do Mathematica, exceto que os intervalos de Julia já estão no formato desejado, portanto é ainda mais curto. Também retorna uma coleção de números. Exemplo de saída:

11-element StepRange{Rational{Int64},Rational{Int64}}:
 -3//1,-5//2,-2//1,-3//2,-1//1,-1//2,0//1,1//2,1//1,3//2,2//1

Observe que os números inteiros são exibidos com 1 no denominador e uma barra dupla é usada para frações. Para obter a saída exatamente como definido na pergunta, é necessário mais código:

f(a,b,c)=map(x->println(x.num,x.den<2?"":"/$(x.den)"),a:c:b)
Fengyang Wang
fonte
3

Matlab com caixa de ferramentas simbólica / oitava com SymPy, 27 bytes

Obrigado a @sanchises por apontar um erro, agora corrigido

@(a,b,c)sym(union(a:c:b,b))

Esta é uma função anônima. Para chamá-lo, atribua a uma variável ou use ans.

Exemplo:

>> @(a,b,c)sym(union(a:c:b,b))
ans = 
    @(a,b,c)sym(union(a:c:b,b))
>> ans(-2,3,1/2)
ans =
[ -2, -3/2, -1, -1/2, 0, 1/2, 1, 3/2, 2, 5/2, 3]
Luis Mendo
fonte
Isso não está de acordo com as especificações, pois o limite superior nem sempre é incluído (tente o exemplo 2).
Sanchises
Obrigado! Corrigido agora
Luis Mendo
E também acho que cvocê pode usar, cito, o tipo que melhor se adequa ao seu idioma para representar os incrementos de fração [...] ou p / e . Eu acho que é bem claro que symbolicé uma opção lógica e permitida (o @VisualBean pode querer confirmar isso). O resultado do operador de dois pontos é então 'atualizado' para uma symbolicmatriz, o que significa que você pode se livrar sym()completamente da chamada.
Sanchises
@sanchises Obrigado, eu já pediu esclarecimentos
Luis Mendo
2

Javascript, 108 90 86   81 bytes

(a,b,n,d)=>{var s="";for(a=a*d;a<b*d;a+=n)s+=(a%d?a+"/"+d:a/d)+" ";s+=b;return s}

Uma função anônima. Após a atribuição a uma variável nomeada com espaço em branco:

var f=(a,b,n,d)=>
{ var s="";
  for(a=a*d; a<b*d; a+=n)
    s+= (a%d ? a + "/" + d : a/d) + " ";
  s+=b;
  return s
}

Exemplos de teste:

console.log(f(1,2,1,8)); //writes:
1 9/8 10/8 11/8 12/8 13/8 14/8 15/8 2

console.log(f(-3,3,4,7)); // writes:
-3 -17/7 -13/7 -9/7 -5/7 -1/7 3/7 1 11/7 15/7 19/7 3 

Uma abordagem imperativa usando javascript, sem recursão, biblioteca ou programação funcional.

traktor53
fonte
1

Smalltalk - 89 bytes

Pela primeira vez, o Smalltalk é quase competitivo!

Number extend[p:e q:i[|h|self to:e by:i do:[:x|h:=x. x printNl].h=e ifFalse:[e printNl]]]

Ligue assim:

> 2 p:5 q:1/2
2
5/2
3
7/2
4
9/2
5

> 1 p:2 q:2/3
1
5/3
2

fonte
1

R - 71 bytes

Supõe que você já instalou o MASSpacote

f=function(x,y,z)MASS::fractions(union(seq(x,y,eval(parse(text=z))),y))

> f(1, 2, '1/3')
[1]   1 4/3 5/3   2
> f(2, 5, '1/2')
[1]   2 5/2   3 7/2   4 9/2   5
bouncyball
fonte
1

Pyret, 56 bytes

{(b,e,n,d):link(e,map(_ / d,range(b * d, e * d))).sort()}

Toma no início (b), final (e), numerador (n) e denominador (d). Cria um intervalo de números inteiros, divide-os e anexa o final da lista (vinculando e classificando).

MLavrentyev
fonte