2015-05-13 3 views
6

Desidero scrivere una funzione in Python che restituisca la moltiplicazione di n funzioni (f1(x) * f2(x) * f3(x) * ... * fn(x)).Mutiplicazione di n funzioni

Stavo pensando a qualcosa di simile:

def mult_func(*args): 
    return lambda x: args(0)(x) * args(1)(x) ... 

ma non so esattamente come scorrere le funzioni n in args.

Grazie.

+4

'per func in args: prod * = func (x)'? – Veedrac

risposta

6

è molto semplice - basta usare ridurre:

from operator import mul  

def mult_func(*args): 
    return lambda x: reduce(mul, (n(x) for n in args), 1) 

Questo è solo un generatore di espressione scorrendo le funzioni, e riducendo di moltiplicazione.

+4

Utilizzare invece 'operator.mul'; non c'è garanzia che le funzioni restituiscano numeri interi. – chepner

+0

@chepner ah, buon punto, grazie. – Maltysen

+0

'operator.mul' è molto più efficiente dell'equivalente espressione' lambda'; casi come questo sono il motivo per cui i moduli 'operator' espongono gli operatori come funzioni. – chepner

5

args è solo una tupla, ma sarà difficile iterare su di esse nel modo in cui è necessario in un'espressione lambda (a meno che non si usi reduce). Definire invece una funzione nidificata.

def mult_func(*args): 
    def _(x): 
     rv = 1 
     for func in args: 
      rv *= func(x) 
     return rv 
    return _ 
+0

È davvero necessaria una funzione annidata? Non sarebbe più semplice mantenere un totale parziale in una variabile mentre itera su args? –

+2

Sulla base dei tentativi dell'OP, ho pensato che cercava una funzione che avrebbe creato una funzione che calcolasse il prodotto, piuttosto che calcolare immediatamente un prodotto per un particolare valore di 'x'. ('f = mult_func (f1, f2, f3); f (3) == f1 (3) * f2 (3) * f3 (3)') – chepner

2
def mult_func(x, *args): 
    total = 1 
    for func in args: 
     total *= func(x) 
    return total 

rendimenti molto semplicemente il prodotto di tutti args con l'input di x.

esempio rapida:

def square(n): 
    return n**2 

>>> print mult_func(2, square, square) 
16 
>>> print mult_func(2, square, square, square) 
64 
0

E 'quell'ora di notte, quindi ecco una soluzione reciprocamente ricorsivo:

def multiply_funcs(funcs): 
    def inner(x): 
     if not funcs: 
      return 1 
     return funcs[0](x) * multiply_funcs(funcs[1:])(x) 
    return inner 
+1

Non dovrebbe restituire 1 e non x se funcs è vuoto. ... perché 1 è l'identità della moltiplicazione? – Shashank

+0

Inoltre si dovrebbe usare la sintassi dell'asterisco poiché è più flessibile. Questo può essere fatto sostituendo funcs con * funcs nella lista dei parametri e sostituendo (funcs [1:]) con (* funcs [1:]). – Shashank

+0

Altrimenti, bella soluzione ... ma vai a letto :) – Shashank