जेफिरनेट लोगो

Tensorflow में अपने ResNet को खरोंच से कैसे कोडित करें? 

दिनांक:

इस लेख के एक भाग के रूप में प्रकाशित किया गया था डेटा साइंस ब्लॉगथॉन

परिचय

हम सभी ने छवि पहचान के लिए ResNets के बारे में सुना है और, हम में से कई लोगों को लगता है कि ResNets शुरुआत में डराने वाला हो सकता है। ResNet का आर्किटेक्चर पहले तो बहुत बड़ा और जटिल दिखता है, लेकिन एक बार जब आप ResNets के पीछे की मूल अवधारणा को समझ जाते हैं तो आप इसके साथ चमत्कार कर सकते हैं।

इस ब्लॉग में हम निम्नलिखित बिंदुओं पर गौर करने जा रहे हैं:

  1. रेसनेट क्या हैं?
  2. ResNets के विभिन्न प्रकार क्या हैं?
  3. Tensorflow में ResNet को कैसे कोड करें?
स्क्रैच से रेसनेट

ResNets क्या हैं और उनके प्रकार?

ResNets को अवशिष्ट नेटवर्क कहा जाता है। ResNet एक विशेष प्रकार का कन्वेन्शनल न्यूरल नेटवर्क (CNN) है जिसका उपयोग इमेज रिकॉग्निशन जैसे कार्यों के लिए किया जाता है। रेसनेट को पहली बार 2015 में कैमिंग हे, जियानग्यु झांग, शाओकिंग रेन और जियान सन ने अपने पेपर - "डीप रेजिडुअल लर्निंग फॉर इमेज रिकॉग्निशन" में पेश किया था।

नेटवर्क की गहराई के आधार पर विभिन्न प्रकार के ResNets विकसित किए जा सकते हैं जैसे ResNet-50 या ResNet-152। ResNet के अंत में मौजूद संख्या नेटवर्क में परतों की संख्या या नेटवर्क कितने गहरे हैं, निर्दिष्ट करती है। हम ResNet के बुनियादी बिल्डिंग ब्लॉक्स का उपयोग करके किसी भी गहराई के साथ ResNet डिज़ाइन कर सकते हैं, जिस पर हम आगे विचार करेंगे:

ResNet को VGG आर्किटेक्चर का उन्नत संस्करण कहा जा सकता है, उनके बीच का अंतर ResNets में उपयोग किए जाने वाले स्किप कनेक्शन का है। नीचे दिए गए चित्र में, हम VGG के आर्किटेक्चर के साथ-साथ 34 लेयर ResNet को भी देख सकते हैं।

रेसनेट 34 आर्किटेक्चर | स्क्रैच से रेसनेट
1 अंजीर. रेसनेट-34 और वीजीजी-19 आर्किटेक्चर 

अब आप सोच रहे होंगे कि हम स्किप कनेक्शन का उपयोग क्यों करते हैं, इसका क्या उद्देश्य है? तो आपके प्रश्न का उत्तर होगा, पहले के सीएनएन आर्किटेक्चर में जैसे-जैसे न्यूरल नेटवर्क में अधिक से अधिक परतें जोड़ी गईं, यह देखा गया कि मॉडल का प्रदर्शन गिरना शुरू हो गया, ऐसा गायब होने वाली ग्रेडिएंट समस्या के कारण था। जैसे-जैसे हम नेटवर्क में गहराई तक गए, गायब होने वाली ग्रेडिएंट समस्या अधिक से अधिक महत्वपूर्ण हो गई और इस समस्या का समाधान स्किप कनेक्शन का उपयोग करना था। स्किप कनेक्शन और उनके पीछे के गणित के बारे में अधिक जानने के लिए आप इसका संदर्भ ले सकते हैं काग़ज़.

पहचान और कनवल्शन ब्लॉक | स्क्रैच से रेसनेट
चित्र 2. ResNet में पहचान और कनवल्शन ब्लॉक

चित्र 2 में हम देख सकते हैं कि एक स्किप कनेक्शन कैसे काम करता है, स्किप कनेक्शन कुछ परतों से प्रशिक्षण छोड़ता है और फिर इसे आउटपुट से जोड़ता है। इससे नेटवर्क को उन परतों को छोड़ने में मदद मिलती है, जो मॉडल के प्रदर्शन को नुकसान पहुंचा रही हैं। यह हमें लुप्त होती ग्रेडिएंट की समस्या का सामना किए बिना नेटवर्क में गहराई तक जाने की अनुमति देता है।

चित्र 2 में हम दो प्रकार के स्किप कनेक्शन देख सकते हैं, बाईं ओर के ब्लॉक को ए कहा जाता है पहचान ब्लॉक और, दाईं ओर के ब्लॉक को a कहा जाता है बॉटलनेक / कनवल्शनल ब्लॉक. दो ब्लॉकों के बीच अंतर यह है कि आइडेंटिटी ब्लॉक सीधे आउटपुट में अवशेष जोड़ता है, जबकि कनवल्शनल ब्लॉक आउटपुट में जोड़ने से पहले अवशेष पर बैच सामान्यीकरण के बाद एक कनवल्शन करता है।

पहचान ब्लॉक संरचना और कोड

अब, आइए इस पहचान ब्लॉक को समझें, प्रत्येक पहचान ब्लॉक का आर्किटेक्चर/एल्गोरिदम इस प्रकार है: (चित्र 3 देखें)

पहचान ब्लॉक संरचना
चित्र 3. रेसनेट में पहचान ब्लॉक

पहचान ब्लॉक के लिए एल्गोरिदम

 X_स्किप = इनपुट
 संवेगात्मक परत (3X3) (पैडिंग='समान') (फ़िल्टर = एफ) →(इनपुट)
 बैच सामान्यीकरण →(इनपुट)
 रेलु सक्रियण →(इनपुट)
 संवेगात्मक परत (3X3) (पैडिंग = 'समान') (फ़िल्टर = एफ) →(इनपुट)
 बैच सामान्यीकरण →(इनपुट)
 जोड़ें (इनपुट + X_स्किप)
 रेलु सक्रियण

 

आपको आश्चर्य हो सकता है कि हमने केवल सभी कनवल्शन परतों के लिए पैडिंग को 'समान' क्यों लिया है। इसके पीछे कारण यह है कि हमें अपने इनपुट का आकार तब तक बनाए रखना होता है जब तक हम उसे अवशेष में नहीं जोड़ देते। यदि इनपुट का आकार बदल जाता है, तो हमें एक Numpy Error मिलेगा, जिसमें लिखा होगा- "अलग-अलग आकार वाले दो सरणियाँ नहीं जोड़ी जा सकतीं"।

उदाहरण के लिए, इनपुट आकार = (24 * 24) पर विचार करें, इसलिए हमारे अवशेष का आकार = (24 * 24) जब हम इस इनपुट पर (3, 3) का कर्नेल लागू करते हैं, तो आउटपुट आकार = (22 * 22) लेकिन हमारे अवशेषों का आकार अभी भी (24*24) ही रहेगा जिससे जोड़ना असंभव हो जाएगा क्योंकि उनके आकार अलग-अलग हैं। ध्यान दें कि (1,1) कन्वेक्शन फिल्टर वाली परतों को पैडिंग की आवश्यकता नहीं है क्योंकि कर्नेल आकार (1 * 1) इनपुट के आकार को नहीं बदलेगा। उपरोक्त उदाहरण के संदर्भ के लिए इस सूत्र को देखें।

आउटपुट आकार के लिए सूत्र | स्क्रैच से रेसनेट

चित्र 4. कनवल्शन के बाद आउटपुट आकार का सूत्र

पहचान ब्लॉक के लिए कोड

अब इस ब्लॉक को केरस की मदद से टेन्सरफ़्लो में कोड करते हैं। इस कोड को निष्पादित करने के लिए आपको निम्नलिखित आयात करने की आवश्यकता होगी:

टीएफ के रूप में टेंसरफ़्लो आयात करें, एनपी के रूप में सुन्न आयात करें, पीएलटी के रूप में matplotlib.pyplot आयात करें
def पहचान_ब्लॉक(x, फ़िल्टर): # टेंसर को x_skip नामक वेरिएबल में कॉपी करें x_स्किप = x # परत 1 x = tf.keras.layers.Conv2D(फ़िल्टर, (3,3), पैडिंग = 'समान')(x) x = tf.keras.layers.BatchNormalization(axis=3)(x) x = tf.keras.layers.Activation('relu')(x) # परत 2 x = tf.keras.layers.Conv2D(फ़िल्टर, (3,3, 3), पैडिंग = 'समान')(x) x = tf.keras.layers.BatchNormalization(axis=XNUMX)(x) # अवशेष जोड़ें x = tf.keras.layers.Add()([x, x_skip]) x = tf.keras.layers.Activation('relu')(x) रिटर्न x

34-लेयर रेसनेट के पहचान ब्लॉक के लिए कोड

कन्वेन्शनल ब्लॉक संरचना और कोड

अब जब हमने पहचान ब्लॉक को कोडित कर लिया है तो आइए कन्वेन्शनल ब्लॉक की ओर बढ़ते हैं, कन्वेन्शनल ब्लॉक के लिए आर्किटेक्चर/एल्गोरिदम इस प्रकार है: (चित्र 5 देखें)

संवेगात्मक ब्लॉक

चित्र 5. रेसनेट में कन्वेन्शनल ब्लॉक

कनवल्शनल ब्लॉक के लिए एल्गोरिदम

 X_स्किप = इनपुट
 संवेगात्मक परत (3X3) (स्ट्राइड्स = 2) (फ़िल्टर = एफ) (पैडिंग = 'समान') →(इनपुट)
 बैच सामान्यीकरण →(इनपुट)
 रेलु सक्रियण →(इनपुट)
 संवेगात्मक परत (3X3) (फ़िल्टर = एफ) (पैडिंग = 'समान') →(इनपुट)
 बैच सामान्यीकरण →(इनपुट)
 संवेगात्मक परत (1X1) (फ़िल्टर = एफ) (स्ट्राइड्स = 2) →(X_स्किप)
 जोड़ें (इनपुट + X_स्किप)
 रेलु सक्रियण

 

इस कनवल्शन ब्लॉक में ध्यान देने योग्य कुछ बिंदु हैं, अवशेषों को सीधे आउटपुट में नहीं जोड़ा जाता है, बल्कि एक कनवल्शन लेयर के माध्यम से पारित किया जाता है। इन परतों में प्रगति का उपयोग छवि के आकार को कम करने के लिए किया जाता है। पहचान ब्लॉक के समान, हमें यह सुनिश्चित करना होगा कि इनपुट और अवशेष का आकार समान हो तो आइए एक उदाहरण के साथ इसकी पुष्टि करें। गणनाओं की क्रॉस-चेकिंग के लिए चित्र 4 देखें।

इनपुट आकार = (24, 24), अवशेष आकार = (24, 24) ConvResidue1 के बाद → इनपुट आकार = (13, 13) * स्ट्राइड = 2 ConvInput2 के बाद → इनपुट आकार = (13, 13) ConvResidue1 के बाद → अवशेष आकार = ( 13, 13) *कदम = 2

जैसा कि हम देख सकते हैं कि इनपुट आकार और अवशेष आकार समान आयामों के साथ समाप्त होते हैं, अब हम इस ब्लॉक को कोड करना शुरू कर सकते हैं।

कनवल्शनल ब्लॉक के लिए कोड

def convolutional_block(x, फ़िल्टर): # टेंसर को x_skip नामक वेरिएबल में कॉपी करें x_स्किप = x # परत 1 x = tf.keras.layers.Conv2D(फ़िल्टर, (3,3), पैडिंग = 'समान', स्ट्राइड्स = (2,2, 3))(x) x = tf.keras.layers.BatchNormalization(axis=2)(x) x = tf.keras.layers.Activation('relu')(x) # लेयर 2 x = tf.keras.layers .Conv3,3D(फ़िल्टर, (3), पैडिंग = 'समान')(x) x = tf.keras.layers.BatchNormalization(axis=1,1)(x) # conv(2) x_skip = tf के साथ अवशेषों को संसाधित करना .keras.layers.Conv1,1D(फ़िल्टर, (2,2), स्ट्राइड्स = (XNUMX))(x_स्किप) # अवशेष जोड़ें x = tf.keras.layers.Add()([x, x_skip]) x = tf .keras.layers.Activation('relu')(x) रिटर्न x

34-लेयर रेसनेट में कन्वेन्शनल ब्लॉक के लिए कोड

रेसनेट-34 संरचना और कोड

रेसनेट34

चित्र 6. 34-परत, 50-परत, 101-परत रेसनेट आर्किटेक्चर

आइए अब चित्र 6 में दिए गए आर्किटेक्चर का अनुसरण करें और एक ResNet-34 मॉडल बनाएं। इस ब्लॉक को कोड करते समय हमें यह ध्यान रखना होगा कि ResNet के प्रत्येक ब्लॉक के पहले ब्लॉक में एक कन्वेन्शनल ब्लॉक होगा और उसके बाद conv2 ब्लॉक को छोड़कर आइडेंटिटी ब्लॉक होंगे। उदाहरण के लिए, चित्र 6 में उल्लिखित आर्किटेक्चर में, conv3 ब्लॉक में 4 उप-ब्लॉक हैं। तो, पहला उप-ब्लॉक कनवल्शनल ब्लॉक होगा, जिसके बाद 1 आइडेंटिटी ब्लॉक होंगे। संदर्भ के लिए, आप वापस जा सकते हैं और चित्र 3 देख सकते हैं। जहां ठोस काली रेखाएं एक पहचान ब्लॉक का प्रतिनिधित्व करती हैं। बिंदीदार काली रेखा एक कन्वेन्शनल ब्लॉक का प्रतिनिधित्व करती है।

अब हम ResNet-34 बनाने के लिए आइडेंटिटी और कनवल्शनल ब्लॉक्स को मिलाएंगे जिन्हें हमने पहले कोड किया था। तो, अब इसे कोड करते हैं।

def ResNet34(आकार = (32, 32, 3), वर्ग = 10): # चरण 1 (सेटअप इनपुट परत) x_input = tf.keras.layers.Input(shape) x = tf.keras.layers.ZeroPadding2D((3 , 3))(x_input) # चरण 2 (मैक्सपूल के साथ आरंभिक कनव परत) x = tf.keras.layers.Conv2D(64, कर्नेल_आकार=7, स्ट्राइड्स=2, पैडिंग='समान')(x) x = tf .keras.layers.BatchNormalization()(x) x = tf.keras.layers.Activation('relu')(x) x = tf.keras.layers.MaxPool2D(pool_size=3, strides=2, padding='same ')(x) # उप-ब्लॉकों का आकार और प्रारंभिक फ़िल्टर आकार ब्लॉक_लेयर्स = [3, 4, 6, 3] फ़िल्टर_साइज़ = 64 # चरण 3 श्रेणी (4) में i के लिए रेज़नेट ब्लॉक जोड़ें: यदि i == 0 : # सब-ब्लॉक के लिए 1 अवशिष्ट/कन्वेल्यूशनल ब्लॉक की जरूरत नहीं है, रेंज में j के लिए (ब्लॉक_लेयर[i]): x = पहचान_ब्लॉक(x, फ़िल्टर_साइज) अन्यथा: # एक अवशिष्ट/कन्वेल्यूशनल ब्लॉक के बाद आइडेंटिटी ब्लॉक # फिल्टर का आकार जाएगा 2 के कारक से बढ़ने पर फ़िल्टर_साइज़ = फ़िल्टर_साइज़*2 x = कनवल्शनल_ब्लॉक(x, फ़िल्टर_साइज़) j के लिए रेंज में (ब्लॉक_लेयर्स[i] - 1): x = पहचान_ब्लॉक(x, फ़िल्टर_साइज़) # चरण 4 अंत डेंस नेटवर्क x = tf .keras.layers.AveragePooling2D((2,2), पैडिंग = 'समान')(x) x = tf.keras.layers.Flatten()(x) x = tf.keras.layers.Dense(512, सक्रियण = 'relu')(x) x = tf.keras.layers.Dense(वर्ग, सक्रियण = 'सॉफ्टमैक्स')(x) मॉडल = tf.keras.models.Model(इनपुट = x_input, आउटपुट = x, नाम = "ResNet34 ") वापसी मॉडल

ResNet34 मॉडल के लिए कोड

अब आप कोड को एक साथ रख सकते हैं और चला सकते हैं। इसके अलावा, मॉडल सारांश पर भी एक नजर डालें। यह 'model.summary()' का उपयोग करके किया जा सकता है जो आपको हमारे आर्किटेक्चर की सभी परतों का विवरण दिखाएगा। अब आप बुनियादी बातों का उपयोग करके विभिन्न प्रकार के रेसनेट बनाने का भी प्रयास कर सकते हैं!

मैंने इस मॉडल को बिना किसी छवि संवर्द्धन के 10 युगों के लिए CIFAR-15 डेटासेट पर प्रशिक्षित किया है। मेरे द्वारा प्राप्त परिणाम इस प्रकार हैं यदि आप मेरे द्वारा उपयोग किए गए कोड को देखने में रुचि रखते हैं, तो आप इस पर जा सकते हैं जुपीटर नोटबुक कागल पर।

क्रॉस एन्ट्रापी हानि

CIFAR-34 डेटासेट पर ResNet-10

निष्कर्ष

तो इस ब्लॉग में, हमने देखा कि ResNets क्या हैं? ResNet के निर्माण खंड क्या हैं? और स्क्रैच से ResNet को कैसे कोड करें? मुझे आशा है कि आपको ब्लॉग पढ़ने में आनंद आया होगा और इससे आपको यह समझने में मदद मिलेगी कि ResNets कैसे काम करता है। यदि आपको यह ब्लॉग पढ़कर अच्छा लगा हो तो इसे अपने साथियों के साथ अवश्य साझा करें। यदि आपको कोई संदेह है या कोड को लागू करने में कठिनाइयों का सामना करना पड़ रहा है, तो आप नीचे एक टिप्पणी छोड़ सकते हैं या मेल द्वारा मुझसे संपर्क कर सकते हैं। लिंक्डइन पर मेरे साथ अवश्य जुड़ें। सभी को सीखने की शुभकामनाएँ!

ईमेल आईडी: [ईमेल संरक्षित] || लिंक्डइन

इस लेख में दिखाया गया मीडिया एनालिटिक्स विद्या के स्वामित्व में नहीं है और लेखक के विवेक पर उपयोग किया जाता है।

प्लेटोए. Web3 फिर से कल्पना की गई। डेटा इंटेलिजेंस प्रवर्धित।
एक्सेस करने के लिए यहां क्लिक करें।

Source: https://www.analyticsvidhya.com/blog/2021/08/how-to-code-your-resnet-from-scratch-in-tensorflow%e2%80%8a/

स्पॉट_आईएमजी

नवीनतम खुफिया

स्पॉट_आईएमजी