Uma bolsa , também chamada de multiset, é uma coleção não ordenada. Você pode chamá-lo de um conjunto que permite duplicatas ou de uma lista (ou matriz) que não está ordenada / indexada. Nesse desafio, você é solicitado a implementar operações de bolsa: adição, diferença, multiplicação, divisão, contagem e teste de igualdade.
Operações
As operações especificadas podem não ser convencionais.
- Além disso, combina duas malas em uma, conservando o número total de cada valor
[1,2,2,3] + [1,2,4] = [1,1,2,2,2,3,4]
- A diferença remove de uma sacola cada elemento de outra sacola ou não faz nada se esse elemento não existir
[1,2,2,4] - [1,2] = [2,4]
[1,2,3] - [2,4] = [1,3]
- multiplicação multiplica cada elemento no saco.
[1,2,3,3,4] * 3 = [1,1,1,2,2,2,3,3,3,3,3,3,4,4,4]
2 * [1,3] = [1,1,3,3]
- A divisão é incomum: cada n elementos iguais são colocados em n novas bolsas iguais, elementos que não podem formar um grupo n permanecem na bolsa. Devolva qualquer uma das n novas bolsas.
[1,1,2,2,2] / 2 = [1,2]
[1,2,2,3,3,3] / 3 = [3]
- contagem conta quantas sacolas divisórias podem ser produzidas a partir da sacola de dividendos
[1,1,2,2,2,2,3,3,3] c [1,2,3] = 2
- teste de igualdade verifica se duas malas têm o mesmo número de cada elemento
[1,2,2,3] == [3,2,1,2] = truthy
[1,2,3] == [1,2,2,3] = falsy
(também pode ser usado=
para isso)
Se você estiver usando seus próprios símbolos para os operadores, especifique.
Formatos
As malas serão exibidas como listas do formulário [1,1,2,3,4]
. Você pode usar qualquer outro suporte que não seja quadrado, ou mesmo usar aspas, ou nada. Os elementos serão inteiros (matematicamente, não necessariamente int
) para os fins desta pergunta. As malas não precisam ser classificadas.
O formato de entrada será duas malas ou uma maleta e um número inteiro, com um operador. Você pode especificar seu próprio formato, desde que contenha esses três.
O formato de saída deve ser uma única bolsa do mesmo formato.
Regras
- você não pode usar funções, operações ou bibliotecas internas (incluindo a biblioteca padrão) que já as implementam; não há problema em usar concatenação e multiplicação de lista, pois são por definição operações de lista, não operações de bolsa (que basicamente fazem a mesma coisa)
- lacunas padrão se aplicam
- resposta mais curta ganha
Casos de teste
[1,2,2,3] + [1,2,4]
[1,1,2,2,2,3,4]
[1,2,2,4] - [1,2]
[2,4]
[1,2,3] - [2,4]
[1,3]
[1,2,3,3,4] * 3
[1,1,1,2,2,2,3,3,3,3,3,3,4,4,4]
2 * [1,3]
[1,1,3,3]
[1,1,2,2,2] / 2
[1,2]
[1,2,2,3,3,3] / 3
[3]
[1,1,2,2,2,2,3,3,3] c [1,2,3]
2
[3,2,1,2] == [1,2,2,3]
truthy
[1,2,3] == [1,2,2,3]
falsy
fonte
Respostas:
05AB1E,
9287838277 bytesDividir por operação
Explicação
Adição
Coloque uma sacola na outra e alise-as em uma sacola.
Multiplicação
Verifique se o número está no topo da pilha. Chame isso de X.
Duplique o saco X vezes e junte-o a um saco.
Contagem
Para cada elemento na sacola do divisor, conte o número de ocorrências na sacola de dividendos.
A contagem mínima será o número de sacolas que podemos fazer.
Igualdade
Ordene as duas malas e verifique se são iguais.
Divisão
Conte quantas vezes cada elemento exclusivo ocorre na sacola.
Se ocorrer pelo menos quantas vezes o divisor. Mantenha (nr_of_copies_total // divisor) cópias na sacola.
Diferença
Para cada elemento no subtraendo, classifique-o na frente do minuendo.
Se o subtraendo atual for igual ao primeiro elemento no minuendo, remova-o do minuendo.
fonte
APL (155)
Isso define um operador
∆
'bolsa', que define as operações da bolsa para determinadas funções. Ou seja,+∆
seria adição. Em seguida, ele lê uma linha do teclado e a avalia como uma expressão de APL.As funções são:
+∆
, Adição-∆
subtração×∆
multiplicação÷∆
divisão⊂∆
contando≡∆
, equivalência (embora, devido ao golfe, qualquer função não reconhecida faça equivalência)Explicação:
∆←{
...}
: define um operador∆
:O←⍺⍺
: armazena a função fornecida emO
(⎕CR
não funcionará⍺⍺
diretamente)O←⎕CR'O'
: obtém a representação de string dessa função'+'=O
...:
: para adição,⍺,⍵
: junte as duas listasR[⍋R←
...]
: e classifique o resultado'-'=O:
: para subtração,⍺{
...}⍵
: execute a seguinte função recursiva:⍵≡⍬:⍺
: se o subtraendo estiver vazio, retorne o minuendo⍺/⍨(⍳⍴⍺)≢⍺⍳⊃⍵∇1↓⍵
: caso contrário, remova o primeiro elemento do subtraendo do subtraendo e do minuendo e tente novamente(⍬=⍴⍵)∧K←'×'=O:
para multiplicação e se o argumento correto não for um saco:⍵/⍺
: replica cada elemento no argumento esquerdo pelo argumento direitoK:
: ... e se o argumento certo for um saco:⍺/⍵
: replica cada elemento no argumento da direita pelo argumento da esquerda (para que a multiplicação seja comutativa)'÷'=O:
: para divisão,⍵≤⍺∘.+⍺
: veja quais elementos em ⍺ ocorrem pelo menos ⍵ vezes,⍺/⍨
: selecione aqueles de ⍺,∪
: e remova todas as duplicatas dessa lista'⊂'=O:
: para contar,⍵{
...}⍺
: execute a seguinte função recursiva:(∪⍺)≢∪⍵:0
: se uma lista contém elementos que a outra não, o resultado é 01+⍺∇⍵-∆⍺
: caso contrário, subtraia o dividendo do divisor, tente novamente e aumente o resultado.⋄
: se nenhuma das opções acima, faça o teste de equivalência:⍺[⍋⍺]≡⍵[⍋⍵]
: classifique as duas listas e veja se são iguais⎕
: lê uma expressão do teclado, avalia-a e gera o resultado.Casos de teste:
fonte
[2,2,2,2,2,2]/3
deve dar[2,2]
, mas a sua parece dar[2]
.∆
, o usuário será despejado no REPL nativo da APL, onde∆
agora é válido. Eu acho que você pode salvar alguns bytes movendo a subtração para o final, pois é o único que requer duas linhas. Em vez de⎕CR
, use*
para simbolizar contagem, e façaO←⍺⍺2
, então2=O:
para mais,1=O
para mult,0=O:
para equiv,7<O:
para contagem e0<O:
para div (com implícito0>O:
para subtr).JavaScript (ES6), 260 bytes
Leva 3 parâmetros. O primeiro parâmetro é uma matriz, o segundo é um operador e o terceiro depende do operador. São necessários sacos para armazenar números inteiros não negativos.
Ungolfed:
fonte
Octave,
253244226 bytesEsta função deve estar em um arquivo. Para escrever a função na janela de comando, você deve usar
endfunction
ouend
.Agradecemos a Luis Mendo por salvar 18 bytes.
As operações são:
Exemplo de uso:
Ungolfed:
fonte
Mathematica,
387347300284 bytesLigeiramente degolfado (também conhecido como versão antiga), não tinha suporte total para testes de igualdade (retornou valores verdadeiros, mas foi deixado sem avaliação para bolsas não correspondentes).
Implementa o tipo de dados necessário com o cabeçalho
b
.Primeiro
b
é definido como sendoOrderless
. Qualquer objeto passado para o kernel com cabeça classificaráb
automaticamente seus argumentos. Portanto, mesmo seb[3,2,1]
digitado, o avaliador nunca verá outra coisa senãob[1,2,3]
.A adição é trivialmente definida como unir os elementos.
Uma regra especial para a diferença de duas malas é definida (explicada abaixo). A versão anterior tinha um símbolo auxiliar para expressões de forma
-bag
.Então a multiplicação (contanto que
n
seja um número inteiro positivo) é recursivamente definida, on*b[...] = b[...] + (n-1)*b[...]
que eventualmente reduzirá a uma soma simples.A regra especial para
b[...] - b[...]
conta o número de elementos distintos na soma dos sacos e subtrai o saco a ser subtraído duas vezes desse resultado. Mais fácil de explicar:Acima está uma lista de
Keys->Values
.KeyValueMap
comTable
cria listas de cadaKey
Value
vez. (tambémMax[...,0]
existe um para não tentar criar tabelas de comprimento negativo). Isso sai como:que é achatado e a cabeça
List
é substituída porb
.A divisão por números inteiros é um pouco semelhante nas funções usadas, é simplesmente a divisão do elemento contada pelo número inteiro.
Divisão por conjuntos ou contando Eu mudei desde a implementação original. Agora é feito recursivamente da seguinte maneira. Digamos, dividimos o saco
b1
porb2
(que no código golfado sãoc
ea
respectivamente. Se(b1-b2) + b2 == b1
, adicione 1 e adicione o resultado da divisão(b1-b2)/b2
. Se não, retorne 0 e saia da recursão.Se as malas coincidirem, a built-in é
==
fornecidaTrue
. A última linha força aFalse
se não o fizerem.Casos de teste:
fonte
Q - 219 caracteres
a
por adição,s
por diferença (subtração),m
por multiplicação,d
por divisão,c
por contagem,e
por igualdade.O algoritmo de adição é óbvio, apenas juntando as malas.
A função de subtração indexa na bolsa de entrada (representada como uma matriz) com todo o intervalo de índice, exceto os primeiros
n
índices de cada classe de equivalência formada por igualdade para cada elemento emy
, onden
é o número de cópias desse representante emy
. O manuseio de possíveis duplicatas oy
torna um verdadeiro monstro de uma função.A função de multiplicação pega
x
valores de cada umy
, no caso dey
um valor único, em vez de uma matriz, apenas os replica.A função de divisão produz os valores cuja contagem na matriz é maior que
y
e remove as duplicatas.A função de contagem calcula as contagens de cada elemento
y
e retorna o mínimo.Duas bolsas são iguais se as representações de matriz ordenadas forem iguais.
fonte
Ruby, resposta de definição de classe,
323291 bytesPrincipalmente, só queria fazer da
Bag
classe uma verdadeira, devido à flexibilidade de Ruby com as classes. Nesse caso, ele é herdadoArray
porque é mais curto do que ter que inicializar uma matriz interna e lidar com outras coisas.Provavelmente darei uma resposta mais séria ao golfe, que usa uma função para lidar com as operações amanhã. Estou muito cansado e me diverti muito com isso
, apesar de ter que discutir com a definição da classenuméricaNumber * Bag
para começar afuncionar adequadamente.Experimente online! (O espaço em branco não importa em Ruby, portanto, o código é um pouco sem uso de lá).
fonte
Ruby, 201 bytes
Como prometido na minha outra resposta, aqui está uma que usa funções em vez de criar uma nova classe. Estou tão perto de violar a marca de 200 bytes ... Experimente on-line
Ele usa os mesmos opcodes que @Neil em sua resposta JavaScript e a mesma ordem de argumentos (lhs, opcode, rhs)
O código:
fonte
C ++,
555551 bytes(quebras de linha adicionadas para facilitar a leitura - somente a primeira nova linha é necessária e contada)
Explicação
Implementamos nossa bolsa como um mapa de (valor, contagem). As operações básicas podem ser implementadas manipulando as contagens; subtração e divisão inteira também precisam remover todos os elementos cuja contagem chega a zero, para que
std::map::operator==
funcione como teste de igualdade.O código expandido a seguir é uma versão genérica dos itens acima, muito menos eficientes: usamos um separado
s()
para extrair quaisquer valores de contagem zero e implementamosconst
operações em termos de operadores de atribuição da maneira idiomática em C ++. Também usamoss()
para fazer a multiplicação0
retornando uma bolsa verdadeiramente vazia (testada adicionando(B{1}*0 != B{})
amain()
); o original falha neste teste e não está claro se é um requisito.Testes
fonte
Python 2.7 - 447B (tamanho do arquivo)
Esta é a minha primeira tentativa no Codegolf, espero que satisfaça. Eu precisava de 2h. (Mas eu ainda sou iniciante em Python)
Edit: Obrigado a "Kevin Lau - não Kenny" por apontar estes:
Edit: Além disso, economizei espaço substituindo funções por lambdas e novas linhas e recuos com mais ponto e vírgula.
Código:
Verificações:
Saída:
Eu poderia tentar outra hora com o set como base algum tempo. Edit: Talvez eu até tente apenas com funções.
fonte
self
- algo comoS
faria também. Outro truque é que asorted
função interna faz exatamente o que você deseja da sua nova funçãos
, para que você possa renunciar à definição da função (visto que você a usa apenas uma vez). Você nunca precisa,__radd__
porque nunca adiciona não-sacolas com malas, embora ainda precise__rmul__
. Finalmente, você só precisa de um espaço de travessão em vez de quatro, que corta para baixo sua contagem de bytes por um pouco