|
|||||||
|
|
|
![]() |
|
|
Strumenti |
|
|
#1 |
|
Senior Member
Iscritto dal: Aug 2006
Messaggi: 1262
|
[python to C] "Traduzione" codice in C
Salve, ho trovato in rete un codice (non lungo) che vorrei "tradurre" in codice C.
Python lo conosco..ma non cosi tanto:P Non saprei come tradurre questo: def makeMatrix(I, J, fill=0.0): m = [] for i in range(I): m.append([fill]*J) return m Che in pratica ti restituisce I matrici di grandezza J. Es: se I=3, J=4: [[0.0, 0.0, 0.0, 0.0], [0.0, 0.0, 0.0, 0.0], [0.0, 0.0, 0.0, 0.0]] |
|
|
|
|
|
#2 |
|
Senior Member
Iscritto dal: Dec 2005
Messaggi: 558
|
Non l'ho testata e l'ho scritta in 5 min ma dovrebbe essere giusta (a meno di errori di sintassi
Il typedef può essere utile per cambiare il tipo di dati che deve contenere la matrice senza dover fare un find/replace, di solito li metto quando faccio funzioni generiche di questo tipo! Codice:
typedef double datum
void makeMatrix(datum **nMatrix, unsigned int i, unsigned int j, datum fill) {
unsigned int k, l;
nMatrix = (datum **) malloc(sizeof(datum *) * j);
for(k = 0; k < j; k++) {
nMatrix[k] = (datum *) malloc(sizeof(datum) * i);
for(l = 0; l < i; l++) {
nMatrix[k][l] = fill;
}
}
}
|
|
|
|
|
|
#3 | |
|
Senior Member
Iscritto dal: Jan 2002
Città: Germania
Messaggi: 26110
|
Quote:
Codice:
def makeMatrix(I, J, fill=0.0):
return [[fill] * J for i in xrange(I)]
__________________
Per iniziare a programmare c'è solo Python con questo o quest'altro (più avanzato) libro @LinkedIn Non parlo in alcun modo a nome dell'azienda per la quale lavoro Ho poco tempo per frequentare il forum; eventualmente, contattatemi in PVT o nel mio sito. Fanboys |
|
|
|
|
|
|
#4 |
|
Member
Iscritto dal: Jul 2008
Messaggi: 237
|
Bisogna considerare che in C comunque bisogna allocare memoria nello heap esplicitamente quindi è anche possibile ritornare un risultato esplicitamente, ma dopo l'uso del risultato bisognerà chiamare free sul puntatore ritornato dalla funzione. Questo rende necessario l'uso di pattern quali quello suggerito nella soluzione dove è necessario passare un puntatore alla memoria in cui scrivere il risultato.
|
|
|
|
|
|
#5 | |
|
Senior Member
Iscritto dal: Aug 2006
Messaggi: 1262
|
Quote:
grazie |
|
|
|
|
|
|
#6 |
|
Member
Iscritto dal: Jul 2008
Messaggi: 237
|
datum diventa semplicemente un alias per double, in questo caso. In caso dovessi tu un giorno decidere che vuoi operare su una matrice di interi, tuttavia, ti basterebbe cambiare il double del typedef con int. E così via...
|
|
|
|
|
|
#7 |
|
Senior Member
Iscritto dal: Aug 2006
Messaggi: 1262
|
scusate la mia ignoranza..ma i due * che significano? (super puntatore?
grazie |
|
|
|
|
|
#8 |
|
Senior Member
Iscritto dal: Oct 2006
Città: milano
Messaggi: 1439
|
|
|
|
|
|
|
#9 |
|
Member
Iscritto dal: Jul 2008
Messaggi: 237
|
Puntatore ad un puntatore. Usato per una matrice bidimensionale visto che ogni dimensione dell'array implica l'aggiunta di un livello di indirection.
|
|
|
|
|
|
#10 |
|
Senior Member
Iscritto dal: Dec 2005
Messaggi: 558
|
come ti hanno già detto i due * indicano puntatori a puntatori. Si può fare anche utilizzando un unico puntatore ma questo ne peggiorerebbe un pochino la leggibilità (secondo me non molto, cmq così è più chiaro)
|
|
|
|
|
|
#11 |
|
Senior Member
Iscritto dal: Aug 2006
Messaggi: 1262
|
ah ok, grazie!!
|
|
|
|
|
|
#12 |
|
Senior Member
Iscritto dal: Aug 2006
Messaggi: 1262
|
avrei un'altra domanda da porvi..in python definisco la class NN, ma poi ho questo:
def __init__(self, ni, nh, no): # number of input, hidden, and output nodes self.ni = ni + 1 # +1 for bias node self.nh = nh self.no = no # activations for nodes self.ai = [1.0]*self.ni self.ah = [1.0]*self.nh self.ao = [1.0]*self.no # create weights self.wi = makeMatrix(self.ni, self.nh) self.wo = makeMatrix(self.nh, self.no) __init__ é una funzione, ma in C che uso? O penso che in questo caso sia meglio parlare di C++, o sbaglio? grazie |
|
|
|
|
|
#13 |
|
Senior Member
Iscritto dal: Jan 2002
Città: Germania
Messaggi: 26110
|
Non sbagli: __init__ è il "costruttore" di una classe in Python.
__________________
Per iniziare a programmare c'è solo Python con questo o quest'altro (più avanzato) libro @LinkedIn Non parlo in alcun modo a nome dell'azienda per la quale lavoro Ho poco tempo per frequentare il forum; eventualmente, contattatemi in PVT o nel mio sito. Fanboys |
|
|
|
|
|
#14 | |
|
Senior Member
Iscritto dal: Aug 2006
Messaggi: 1262
|
Quote:
semplicemente tolgo il def __init__? class NN { self.ni = ni + 1; self.nh = nh; self.no = no; # activations for nodes self.ai = [1.0]*self.ni; self.ah = [1.0]*self.nh; self.ao = [1.0]*self.no; # create weights self.wi = makeMatrix(self.ni, self.nh); self.wo = makeMatrix(self.nh, self.no); e poi dentro scrivo delle funzioni? o chiudo class, e scrivo le funzioni? |
|
|
|
|
|
|
#15 |
|
Senior Member
Iscritto dal: Oct 2007
Città: Padova
Messaggi: 4131
|
Non vorrei dire cazzate, ma potresti tardurre la classe Python con una struct... a quel punto il costruttore (__init__) diventa una normale funzione di inizializzazione della struct.
__________________
As long as you are basically literate in programming, you should be able to express any logical relationship you understand. If you don’t understand a logical relationship, you can use the attempt to program it as a means to learn about it. (Chris Crawford) |
|
|
|
|
|
#16 |
|
Senior Member
Iscritto dal: Dec 2003
Messaggi: 4907
|
|
|
|
|
|
|
#17 |
|
Senior Member
Iscritto dal: Aug 2006
Messaggi: 1262
|
appunto..per c++ che dovrei fare?
|
|
|
|
|
|
#18 |
|
Senior Member
Iscritto dal: Oct 2007
Città: Padova
Messaggi: 4131
|
Ma non si parlava di C, scusa?
Comunque in C++ le classi ci sono eccome, ed è possibile programmare secondo la prospettiva orientata agli oggetti. Quindi puoi tradurre la tua classe Python con una classe C++... Il metodo __init__ di Python diverrà un costruttore nella versione C++ (in cui ti dedi anche preoccupare del distruttore, però). Certo che per fare una traduzione da un linguaggio a un'altro (tra l'altro da un linguaggio che ha un dynamic type system a uno che si basa su uno static type system, tanto per citare una differenza) senza troppi problemi e troppe perdite di tempo credo ci voglia una fondata conoscenza e esperienza in entrambi... Se poi ti devi fiondare su C++, ti ci vuole un santo protettore (prova ad accendere un cero a 'san Cionci', oppure a 'Tommo il martire',
__________________
As long as you are basically literate in programming, you should be able to express any logical relationship you understand. If you don’t understand a logical relationship, you can use the attempt to program it as a means to learn about it. (Chris Crawford) Ultima modifica di banryu79 : 10-06-2009 alle 12:24. |
|
|
|
|
|
#19 |
|
Senior Member
Iscritto dal: Aug 2006
Messaggi: 1262
|
dici che é cosi difficile? perché il codice completo non é cosi complicato:
Codice:
import math
import random
import string
random.seed(0)
# calculate a random number where: a <= rand < b
def rand(a, b):
return (b-a)*random.random() + a
# Make a matrix (we could use NumPy to speed this up)
def makeMatrix(I, J, fill=0.0):
m = []
for i in range(I):
m.append([fill]*J)
return m
# our sigmoid function, tanh is a little nicer than the standard 1/(1+e^-x)
def sigmoid(x):
return math.tanh(x)
# derivative of our sigmoid function, in terms of the output (i.e. y)
def dsigmoid(y):
return 1.0 - y**2
class NN:
def __init__(self, ni, nh, no):
# number of input, hidden, and output nodes
self.ni = ni + 1 # +1 for bias node
self.nh = nh
self.no = no
# activations for nodes
self.ai = [1.0]*self.ni
self.ah = [1.0]*self.nh
self.ao = [1.0]*self.no
# create weights
self.wi = makeMatrix(self.ni, self.nh)
self.wo = makeMatrix(self.nh, self.no)
# set them to random vaules
for i in range(self.ni):
for j in range(self.nh):
self.wi[i][j] = rand(-0.2, 0.2)
for j in range(self.nh):
for k in range(self.no):
self.wo[j][k] = rand(-2.0, 2.0)
# last change in weights for momentum
self.ci = makeMatrix(self.ni, self.nh)
self.co = makeMatrix(self.nh, self.no)
def update(self, inputs):
if len(inputs) != self.ni-1:
raise ValueError, 'wrong number of inputs'
# input activations
for i in range(self.ni-1):
#self.ai[i] = sigmoid(inputs[i])
self.ai[i] = inputs[i]
# hidden activations
for j in range(self.nh):
sum = 0.0
for i in range(self.ni):
sum = sum + self.ai[i] * self.wi[i][j]
self.ah[j] = sigmoid(sum)
# output activations
for k in range(self.no):
sum = 0.0
for j in range(self.nh):
sum = sum + self.ah[j] * self.wo[j][k]
self.ao[k] = sigmoid(sum)
return self.ao[:]
def backPropagate(self, targets, N, M):
if len(targets) != self.no:
raise ValueError, 'wrong number of target values'
# calculate error terms for output
output_deltas = [0.0] * self.no
for k in range(self.no):
error = targets[k]-self.ao[k]
output_deltas[k] = dsigmoid(self.ao[k]) * error
# calculate error terms for hidden
hidden_deltas = [0.0] * self.nh
for j in range(self.nh):
error = 0.0
for k in range(self.no):
error = error + output_deltas[k]*self.wo[j][k]
hidden_deltas[j] = dsigmoid(self.ah[j]) * error
# update output weights
for j in range(self.nh):
for k in range(self.no):
change = output_deltas[k]*self.ah[j]
self.wo[j][k] = self.wo[j][k] + N*change + M*self.co[j][k]
self.co[j][k] = change
#print N*change, M*self.co[j][k]
# update input weights
for i in range(self.ni):
for j in range(self.nh):
change = hidden_deltas[j]*self.ai[i]
self.wi[i][j] = self.wi[i][j] + N*change + M*self.ci[i][j]
self.ci[i][j] = change
# calculate error
error = 0.0
for k in range(len(targets)):
error = error + 0.5*(targets[k]-self.ao[k])**2
return error
def test(self, patterns):
for p in patterns:
print p[0], '->', self.update(p[0])
def weights(self):
print 'Input weights:'
for i in range(self.ni):
print self.wi[i]
print
print 'Output weights:'
for j in range(self.nh):
print self.wo[j]
def train(self, patterns, iterations=1000, N=0.79, M=0.1):
# N: learning rate
# M: momentum factor
for i in xrange(iterations):
error = 0.0
for p in patterns:
inputs = p[0]
targets = p[1]
self.update(inputs)
error = error + self.backPropagate(targets, N, M)
if i % 100 == 0:
print 'error %-14f' % error
def demo():
# Teach network XOR function
pat = [
[[0,1,1,1,0,
1,0,0,0,1,
1,0,0,0,1,
1,1,1,1,1,
1,0,0,0,1,
1,0,0,0,1,
1,0,0,0,1], [1]] ]
pat2 = [
[[1,1,1,1,1,
1,0,0,0,1,
1,0,0,0,1,
1,0,0,0,1,
1,1,1,1,1,
1,0,0,0,1,
1,0,0,0,1]],
]
# create a network with two input, two hidden, and one output nodes
n = NN(35, 3, 1)
# train it with some patterns
n.train(pat)
# test it
n.test(pat2)
if __name__ == '__main__':
demo()
|
|
|
|
|
|
#20 | |
|
Senior Member
Iscritto dal: Oct 2007
Città: Padova
Messaggi: 4131
|
Quote:
Certo ce la puoi fare, ma se non sai niente di C++ la vedo dura, a meno che qualche anima pia non prenda tutta la classe Python che hai postato e ti posti per filo e per segno un equivalente codice C++ della stessa. O più anime pie lo facciano ognuna un pezzetto, a rate. L'alternativa è che tu speda qualche giorno (una settimana) a familiarizzarti con il linguaggio C++, in generale, e in particolare con il costrutto class e i concetti che ci ruotano attorno. Sarebbe bene anche studiare come funzionano le variabili, e i puntatori (facciamo un due settimane, via; presuppongo che tu non sappia niente di C/C++ e di puntatori). Poi provi a realizzare una implementazione di quella classe in C++, e per gli errori/problemi specifici procedi chiedendo aiuto al forum. Se qualcuno mi contraddice dimostrando che ho sparato fanfarate e ti aiuta concretamente sarò solo che felice per te
__________________
As long as you are basically literate in programming, you should be able to express any logical relationship you understand. If you don’t understand a logical relationship, you can use the attempt to program it as a means to learn about it. (Chris Crawford) |
|
|
|
|
|
| Strumenti | |
|
|
Tutti gli orari sono GMT +1. Ora sono le: 00:07.




















