Golf el problema de la suma de subconjuntos


15

Tarea

Dada una lista de enteros delimitados por espacios como entrada, genera todos los subconjuntos únicos no vacíos de estos números que cada subconjunto suma a 0.


Caso de prueba

Entrada: 8 −7 5 −3 −2
Salida:-3 -2 5


Criterio ganador

Este es el , por lo que gana el código más corto en bytes.


1
¿Tenemos que preocuparnos por la unicidad si la entrada contiene números no únicos? En otras palabras, ¿cuántos resultados tengo que imprimir para la entrada 3 3 -3 -3?
Keith Randall

@Keith. Por convención, los conjuntos consisten en elementos distintos que aparecen como máximo una vez. Los conjuntos múltiples pueden tener elementos que aparecen más de una vez. en.wikipedia.org/wiki/Multiset
DavidC

44
@DavidCarraher, OP mezcla terminología al hablar de subconjuntos de listas.
Peter Taylor

@PeterTaylor Gracias. Buen punto.
DavidC

Respuestas:


4

GolfScript, 41 caracteres

~][[]]\{`{1$+$}+%}%;(;.&{{+}*!},{" "*}%n*

Si no le importa el formato de salida específico, puede acortar el código a 33 caracteres.

~][[]]\{`{1$+$}+%}%;(;.&{{+}*!},`

Ejemplo (ver en línea ):

> 8 -7 5 -3 -2 4
-3 -2 5
-7 -2 4 5
-7 -3 -2 4 8

6

Brachylog (2), 9 caracteres

{⊇.+0∧}ᵘb

Pruébalo en línea!

{⊇.+0∧}ᵘb
 ⊇           subset
   +0        that sums to 0
  .  ∧       output the subset
{     }ᵘ     take all unique solutions
        b    except the first (which is the empty solution)

4

Python, 119 caracteres

def S(C,L):
 if L:S(C,L[1:]);S(C+[L[0]],L[1:])
 elif sum(map(int,C))==0and C:print' '.join(C)
S([],raw_input().split())

Enumera todos los 2 ^ n subconjuntos de forma recursiva y verifica cada uno.


¡Bravo! Entré en un personaje ...
boothby

3

Python, 120

Soy un personaje peor que la solución de Keith. Pero ... esto está muy cerca de no publicar. Una de mis características favoritas de code-golf es cuán diferentes pueden ser las soluciones de longitud similar.

l=raw_input().split()
print[c for c in[[int(j)for t,j in enumerate(l)if 2**t&i]for i in range(1,2**len(l))]if sum(c)==0]

2

Python ( 128 137 136)

¡Maldita sea itertools.permutations, por tener un nombre tan largo!

Solución de fuerza bruta. Me sorprende que no sea el más corto: pero creo que itertoolsarruina la solución.

Sin golf:

import itertools
initial_set=map(int, input().split())
ans=[]
for length in range(1, len(x)+1):
    for subset in itertools.permutations(initial_set, length):
        if sum(subset)==0:
            ans+=str(sorted(subset))
print set(ans)

Golfed (salida fea):

from itertools import*
x=map(int,input().split())
print set(`sorted(j)`for a in range(1,len(x)+1)for j in permutations(x,a)if sum(j)==0)

Golfed (salida bonita) (183):

from itertools import*
x=map(int,input().split())
print `set(`sorted(j)`[1:-1]for a in range(1,len(x)+1)for j in permutations(x,a)if sum(j)==0)`[5:-2].replace("'","\n").replace(",","")

import itertools as i: importando el módulo itertools y llamándolo i

x=map(int,input().split()): separa la entrada por espacios, luego convierte los elementos de las listas resultantes en enteros (2 3 -5 -> [2, 3, -5])

set ( sorted(j)para a en rango (1, len (x) +1) para j en i.permutations (x, a) if sum (j) == 0):
Devuelve una lista de todos los subconjuntos en x, ordenados, donde la suma es 0, y luego obtiene solo los elementos únicos
( set(...))

Las tumbas (`) alrededor sorted(j)son la abreviatura de Python repr(sorted(j)). La razón por la que esto está aquí es porque los conjuntos en Python no pueden manejar listas, por lo que la siguiente mejor opción es usar cadenas con una lista como texto.


Estoy confundido acerca de cómo obtienes números enteros en lugar de cadenas. split()hace una lista de cadenas, pero luego está llamando suma los subconjuntos de esa división.
Keith Randall

@KeithRandall: facepalm Tenía prisa, así que no probé mi código. Gracias por señalar eso.
beary605

Probablemente puedas salvar a un personaje haciendofrom itertools import*
Matt

En realidad las tumbas es la abreviatura derepr()
gnibbler

@gnibbler: Eso tendría mucho más sentido cuando se ejecuta `` hola ''. ¡Gracias!
beary605

2

C # - 384 caracteres

OK, la programación de estilo funcional en C # no es tan corta , ¡pero me encanta ! (Usando solo una enumeración de fuerza bruta, nada mejor).

using System;using System.Linq;class C{static void Main(){var d=Console.ReadLine().Split(' ').Select(s=>Int32.Parse(s)).ToArray();foreach(var s in Enumerable.Range(1,(1<<d.Length)-1).Select(p=>Enumerable.Range(0,d.Length).Where(i=>(p&1<<i)!=0)).Where(p=>d.Where((x,i)=>p.Contains(i)).Sum()==0).Select(p=>String.Join(" ",p.Select(i=>d[i].ToString()).ToArray())))Console.WriteLine(s);}}

Formateado y comentado para mayor legibilidad:

using System;
using System.Linq;

class C
{
    static void Main()
    {
        // read the data from stdin, split by spaces, and convert to integers, nothing fancy
        var d = Console.ReadLine().Split(' ').Select(s => Int32.Parse(s)).ToArray();
        // loop through all solutions generated by the following LINQ expression
        foreach (var s in
            // first, generate all possible subsets; well, first just their numbers
            Enumerable.Range(1, (1 << d.Length) - 1)
            // convert the numbers to the real subsets of the indices in the original data (using the number as a bit mask)
            .Select(p => Enumerable.Range(0, d.Length).Where(i => (p & 1 << i) != 0))
            // and now filter those subsets only to those which sum to zero
            .Where(p => d.Where((x, i) => p.Contains(i)).Sum() == 0)
            // we have the list of solutions here! just convert them to space-delimited strings
            .Select(p => String.Join(" ", p.Select(i => d[i].ToString()).ToArray()))
        )
            // and print them!
            Console.WriteLine(s);
    }
}

2

SWI-Prolog 84

Esta versión imprime la lista, en lugar de tratar de encontrar un enlace apropiado para un término en un predicado.

s([],O):-O=[_|_],sum_list(O,0),print(O).
s([H|T],P):-s(T,[H|P]).
s([_|T],O):-s(T,O).

Método de entrada

s([8,-7,5,-3,-2,4],[]).

Para el registro, esta es la versión que encuentra un enlace para satisfacer el predicado:

s(L,O):-s(L,0,O),O=[_|_].
s([],0,[]).
s([H|T],S,[H|P]):-R is H+S,s(T,R,P).
s([_|T],S,O):-s(T,S,O).

Método de entrada

s([8,-7,5,-3,-2,4],O).

La revisión anterior contiene una solución incompleta que no logró eliminar el conjunto vacío.


2

Mathematica 62 57 38

Código

Entrada introduce como números enteros en una matriz, x.

x

entrada

Grid@Select[Subsets@x[[1, 1]], Tr@# == 0 &]

Salida

salida


Explicación

x[[1, 1]] convierte la entrada en una lista de enteros.

Subsets genera todos los subconjuntos de los enteros.

Select....Tr@# == 0 da todos los subconjuntos que tienen un total igual a 0.

Grid formatea los subconjuntos seleccionados como enteros separados por espacios.


2

Jalea , 6 bytes

ŒPḊSÐḟ

Pruébalo en línea!

Solo por completo. Al igual que Brachylog, Jelly también es posterior al desafío, pero por ahora, los idiomas más nuevos compiten normalmente.

ŒP       Power set.
  Ḋ      Dequeue, remove the first element (empty set).
    Ðḟ   Filter out the subsets with truthy (nonzero)...
   S       sum.


1

J, 57 53 51 49 caracteres

>a:-.~(#:@i.@(2&^)@#<@":@(#~0=+/)@#"1 _])".1!:1[1

Uso:

   >a:-.~(#:@i.@(2&^)@#<@":@(#~0=+/)@#"1 _])".1!:1[1
8 _7 5 _3 _2 4
5 _3 _2
_7 5 _2 4
8 _7 _3 _2 4

Reescribiendo el tren como (<@":@(#~0=+/)@#"1 _~2#:@i.@^#)salva 4 personajes.
algorithmshark

1

Stax , 8 bytes CP437

â±3╒yΣ╓à

¡Ejecute y depure en línea!

Explicación

Utiliza la versión desempaquetada (9 bytes) para explicar.

LS{|+!fmJ
L            Convert to list
 S           Powerset
  {   f      Filter with block
   |+!       Sum is zero
       mJ    Print each subset, joined by spaces

Given a list of space-delimited integers as input; Sin embargo, está tomando una lista como entrada.
Jonathan Frech

Se solucionará al costo de un byte.
Weijun Zhou

1

J , 34 bytes

(a:-.~](<@#~0=+/)@#~[:#:@i.2^#)@".

Pruébalo en línea!

cómo

".convierte la entrada en una lista. luego:

a: -.~ ] (<@#~ (0 = +/))@#~ [: #:@i. 2 ^ #
                                  i.       NB. ints from 0 to...
                                     2 ^ # NB. 2 to the input len
                            [: #:@         NB. converted to binary masks
       ] (             ) #~                NB. filter the input using
                                           NB. using those masks, giving
                                           NB. us all subsets
         (             )@                  NB. and to each one...
         (  #~ (0 = +/))                   NB. return it if its sum is
                                           NB. 0, otherwise make it 
                                           NB. the empty list.
         (<@           )                   NB. and box the result.
                                           NB. now we have our answers
                                           NB. and a bunch of empty 
                                           NB. boxes, or aces (a:).
a: -.~                                     NB. remove the aces.

1

Perl 6 , 51 bytes

*.words.combinations.skip.grep(!*.sum)>>.Bag.unique

Pruébalo en línea!

Devuelve una lista de bolsas únicas que suman 0. Una bolsa es un conjunto ponderado.

Explicación:

*.words                 # Split by whitespace
 .combinations          # Get the powerset
 .skip                  # Skip the empty list
 .grep(!*.sum)          # Select the ones that sum to 0
 >>.Bag                 # Map each to a weighted Set
 .unique                # And get the unique sets

0

Ruby, 110 bytes

a=gets.split.map &:to_i;b=[];(1...a.length).each{|c|a.permutation(c){|d|d.sum==0?b<<d:0}};p b.map(&:sort).uniq

Agregará el enlace TIO más tarde.

Toma datos de stdin como una lista de números, p. Ej. 8 −7 5 −3 −2

Cómo funciona: Convierte la entrada en una matriz de números. Obtiene todas las permutaciones de las longitudes de 1 a la longitud de la matriz. Los agrega a la matriz de salida si suman 0. Produce la matriz sin duplicados.

Salida para la entrada de muestra: [[-3, -2, 5]]

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.