2017-02-11 5 views
2

Ich lese die Xception Papier (es gibt sogar eine Keras Model für die Beschreibung NN) und es spricht über trennbare Windungen. Ich habe versucht zu verstehen, wie genau sie berechnet werden. Anstatt es auf ungenaue Worte zu beschränken, habe ich den folgenden Pseudocode eingefügt, der mein Verständnis zusammenfasst. Der Code wird von einem Feature-Map 18x18x728 zu einem 18x18x1024 einen:Wie können trennbare Windungen im Xception-Papier berechnet werden?

XSIZE = 18; 
YSIZE = 18; 
ZSIZE = 728; 
ZSIXE2 = 1024; 

float mapin[XSIZE][YSIZE][ZSIZE]; // Input map 
float imap[XSIZE][YSIZE][ZSIZE2]; // Intermediate map 
float mapout[XSIZE][YSIZE][ZSIZE2]; // Output map 

float wz[ZSIZE][ZSIZE2]; // Weights for 1x1 convs 
float wxy[3][3][ZSIZE2]; // Weights for 3x3 convs 

// Apply 1x1 convs 
for(y=0;y<YSIZE;y++) 
    for(x=0;x<XSIZE;x++) 
    for(o=0;o<ZSIZE2;o++){ 
     s=0.0; 
     for(z=0;z<ZSIZE;z++) 
     s+=mapin[x][y][z]*wz[z][o]; 
     imap[x][y][o]=s; 
    } 

// Apply 2D 3x3 convs 
for(o=0;o<ZSIZE2;o++) 
    for(y=0y<YSIZE;y++) 
    for(x=0;x<XSIZE;x++){ 
     s=0.0; 
     for(i=-1;i<2;i++) 
     for(j=-1;j<2;j++) 
      s+=imap[x+j][y+i][o]*wxy[j+1][i+1][o]; // This value is 0 if falls off the edge 
     mapout[x][y][o]=s; 
    } 

Ist das korrekt? Wenn nicht, können Sie Fixes vorschlagen, die ähnlich in C oder Pseudo-C geschrieben sind?

Vielen Dank im Voraus.

Antwort

0

Ich fand tf.nn.separable_conv2d in Tensorflow, die genau dies tut. Also habe ich eine sehr einfache Grafik erstellt und mit Hilfe von Zufallszahlen versucht, den obigen Code zu erhalten, um das Ergebnis zu erreichen. Der korrekte Code ist:

XSIZE = 18; 
YSIZE = 18; 
ZSIZE = 728; 
ZSIXE2 = 1024; 

float mapin[XSIZE][YSIZE][ZSIZE]; // Input map 
float imap[XSIZE][YSIZE][ZSIZE]; // Intermediate map 
float mapout[XSIZE][YSIZE][ZSIZE2]; // Output map 

float wxy[3][3][ZSIZE]; // Weights for 3x3 convs 
float wz[ZSIZE][ZSIZE2]; // Weights for 1x1 convs 


// Apply 2D 3x3 convs 
for(o=0;o<ZSIZE;o++) 
    for(y=0y<YSIZE;y++) 
    for(x=0;x<XSIZE;x++){ 
     s=0.0; 
     for(i=-1;i<2;i++) 
     for(j=-1;j<2;j++) 
      s+=mapin[x+j][y+i][o]*wxy[j+1][i+1][o]; // This value is 0 if falls off the edge 
     imap[x][y][o]=s; 
    } 

// Apply 1x1 convs 
for(y=0;y<YSIZE;y++) 
    for(x=0;x<XSIZE;x++) 
    for(o=0;o<ZSIZE2;o++){ 
     s=0.0; 
     for(z=0;z<ZSIZE;z++) 
     s+=imap[x][y][z]*wz[z][o]; 
     mapout[x][y][o]=s; 
    } 

Der Hauptunterschied besteht in der Reihenfolge, in der die zwei Gruppen von Faltungen durchgeführt werden. Zu meiner Überraschung ist die Reihenfolge wichtig, auch wenn ZSIZE == ZSIZE2.

Verwandte Themen