TensorFlow.org এ দেখুন | Google Colab-এ চালান | GitHub এ দেখুন | নোটবুক ডাউনলোড করুন | TF হাব মডেল দেখুন |
এই টিউটোরিয়ালটিতে প্লেইন-টেক্সট আইএমডিবি মুভি রিভিউগুলির ডেটাসেটে অনুভূতি বিশ্লেষণ করার জন্য BERT-কে ফাইন-টিউন করার সম্পূর্ণ কোড রয়েছে। একটি মডেলকে প্রশিক্ষণ দেওয়ার পাশাপাশি, আপনি শিখবেন কীভাবে পাঠ্যকে একটি উপযুক্ত বিন্যাসে প্রিপ্রসেস করতে হয়।
এই নোটবুকে, আপনি করবেন:
- IMDB ডেটাসেট লোড করুন
- TensorFlow Hub থেকে একটি BERT মডেল লোড করুন
- একটি ক্লাসিফায়ারের সাথে BERT একত্রিত করে আপনার নিজস্ব মডেল তৈরি করুন
- আপনার নিজের মডেলকে প্রশিক্ষণ দিন, এর অংশ হিসেবে BERT-কে ফাইন-টিউনিং করুন
- আপনার মডেল সংরক্ষণ করুন এবং বাক্য শ্রেণীবদ্ধ করতে এটি ব্যবহার করুন
আপনি IMDB, ডেটা সেটটি সঙ্গে কাজ করার জন্য নতুন হন, দয়া করে দেখুন বেসিক টেক্সট শ্রেণীবিন্যাস আরো বিস্তারিত জানার জন্য।
BERT সম্পর্কে
বার্ট এবং অন্যান্য ট্রান্সফরমার এনকোডার আর্কিটেকচারের NLP মধ্যে কাজগুলো বিভিন্ন (প্রাকৃতিক ভাষা প্রক্রিয়াকরণ) এ দুর্দান্তভাবে সফল হয়েছে। তারা প্রাকৃতিক ভাষার ভেক্টর-স্পেস উপস্থাপনা গণনা করে যা গভীর শিক্ষার মডেলগুলিতে ব্যবহারের জন্য উপযুক্ত। মডেলের BERT পরিবার ট্রান্সফর্মার এনকোডার আর্কিটেকচার ব্যবহার করে ইনপুট টেক্সটের প্রতিটি টোকেনকে আগে এবং পরে সমস্ত টোকেনের সম্পূর্ণ প্রসঙ্গে প্রক্রিয়া করতে, তাই নাম: ট্রান্সফরমার থেকে দ্বিমুখী এনকোডার প্রতিনিধিত্ব।
BERT মডেলগুলি সাধারণত পাঠ্যের একটি বৃহৎ কর্পাসে পূর্ব-প্রশিক্ষিত হয়, তারপর নির্দিষ্ট কাজের জন্য সূক্ষ্ম-টিউন করা হয়।
সেটআপ
# A dependency of the preprocessing for BERT inputs
pip install -q -U tensorflow-text
আপনি এর থেকে AdamW অপটিমাইজার ব্যবহার করবে tensorflow / মডেল ।
pip install -q tf-models-official
import os
import shutil
import tensorflow as tf
import tensorflow_hub as hub
import tensorflow_text as text
from official.nlp import optimization # to create AdamW optimizer
import matplotlib.pyplot as plt
tf.get_logger().setLevel('ERROR')
/tmpfs/src/tf_docs_env/lib/python3.7/site-packages/pkg_resources/__init__.py:119: PkgResourcesDeprecationWarning: 0.18ubuntu0.18.04.1 is an invalid version and will not be supported in a future release PkgResourcesDeprecationWarning,
অনুভূতির বিশ্লেষণ
এই নোটবুক ইতিবাচক বা নেতিবাচক হিসেবে শ্রেণীভুক্ত সিনেমা পর্যালোচনা, পর্যালোচনা টেক্সট উপর ভিত্তি করে একটি অনুভূতি বিশ্লেষণ মডেল ট্রেন।
আপনি ব্যবহার করব লার্জ চলচ্চিত্র নিরীক্ষণ ডেটা সেটটি থেকে 50,000 সিনেমা রিভিউ পাঠ্য ধারণ ইন্টারনেট মুভি ডেটাবেজ ।
IMDB ডেটাসেট ডাউনলোড করুন
আসুন ডেটাসেট ডাউনলোড করে এক্সট্র্যাক্ট করি, তারপর ডিরেক্টরির কাঠামোটি অন্বেষণ করি।
url = 'https://ai.stanford.edu/~amaas/data/sentiment/aclImdb_v1.tar.gz'
dataset = tf.keras.utils.get_file('aclImdb_v1.tar.gz', url,
untar=True, cache_dir='.',
cache_subdir='')
dataset_dir = os.path.join(os.path.dirname(dataset), 'aclImdb')
train_dir = os.path.join(dataset_dir, 'train')
# remove unused folders to make it easier to load the data
remove_dir = os.path.join(train_dir, 'unsup')
shutil.rmtree(remove_dir)
Downloading data from https://ai.stanford.edu/~amaas/data/sentiment/aclImdb_v1.tar.gz 84131840/84125825 [==============================] - 7s 0us/step 84140032/84125825 [==============================] - 7s 0us/step
পরবর্তী, আপনি ব্যবহার করবে text_dataset_from_directory
একটি লেবেল তৈরি করতে উপযোগ tf.data.Dataset
।
আইএমডিবি ডেটাসেট ইতিমধ্যেই ট্রেন এবং পরীক্ষায় ভাগ করা হয়েছে, তবে এটির একটি বৈধতা সেটের অভাব রয়েছে। এর ব্যবহারের মাধ্যমে প্রশিক্ষণ ডেটার একটি 80:20 বিভক্ত ব্যবহার করে একটি যাচাইকরণ সেট তৈরি করা যাক validation_split
নিচে যুক্তি।
AUTOTUNE = tf.data.AUTOTUNE
batch_size = 32
seed = 42
raw_train_ds = tf.keras.utils.text_dataset_from_directory(
'aclImdb/train',
batch_size=batch_size,
validation_split=0.2,
subset='training',
seed=seed)
class_names = raw_train_ds.class_names
train_ds = raw_train_ds.cache().prefetch(buffer_size=AUTOTUNE)
val_ds = tf.keras.utils.text_dataset_from_directory(
'aclImdb/train',
batch_size=batch_size,
validation_split=0.2,
subset='validation',
seed=seed)
val_ds = val_ds.cache().prefetch(buffer_size=AUTOTUNE)
test_ds = tf.keras.utils.text_dataset_from_directory(
'aclImdb/test',
batch_size=batch_size)
test_ds = test_ds.cache().prefetch(buffer_size=AUTOTUNE)
Found 25000 files belonging to 2 classes. Using 20000 files for training. Found 25000 files belonging to 2 classes. Using 5000 files for validation. Found 25000 files belonging to 2 classes.
চলুন কয়েকটা রিভিউ দেখে নেওয়া যাক।
for text_batch, label_batch in train_ds.take(1):
for i in range(3):
print(f'Review: {text_batch.numpy()[i]}')
label = label_batch.numpy()[i]
print(f'Label : {label} ({class_names[label]})')
Review: b'"Pandemonium" is a horror movie spoof that comes off more stupid than funny. Believe me when I tell you, I love comedies. Especially comedy spoofs. "Airplane", "The Naked Gun" trilogy, "Blazing Saddles", "High Anxiety", and "Spaceballs" are some of my favorite comedies that spoof a particular genre. "Pandemonium" is not up there with those films. Most of the scenes in this movie had me sitting there in stunned silence because the movie wasn\'t all that funny. There are a few laughs in the film, but when you watch a comedy, you expect to laugh a lot more than a few times and that\'s all this film has going for it. Geez, "Scream" had more laughs than this film and that was more of a horror film. How bizarre is that?<br /><br />*1/2 (out of four)' Label : 0 (neg) Review: b"David Mamet is a very interesting and a very un-equal director. His first movie 'House of Games' was the one I liked best, and it set a series of films with characters whose perspective of life changes as they get into complicated situations, and so does the perspective of the viewer.<br /><br />So is 'Homicide' which from the title tries to set the mind of the viewer to the usual crime drama. The principal characters are two cops, one Jewish and one Irish who deal with a racially charged area. The murder of an old Jewish shop owner who proves to be an ancient veteran of the Israeli Independence war triggers the Jewish identity in the mind and heart of the Jewish detective.<br /><br />This is were the flaws of the film are the more obvious. The process of awakening is theatrical and hard to believe, the group of Jewish militants is operatic, and the way the detective eventually walks to the final violent confrontation is pathetic. The end of the film itself is Mamet-like smart, but disappoints from a human emotional perspective.<br /><br />Joe Mantegna and William Macy give strong performances, but the flaws of the story are too evident to be easily compensated." Label : 0 (neg) Review: b'Great documentary about the lives of NY firefighters during the worst terrorist attack of all time.. That reason alone is why this should be a must see collectors item.. What shocked me was not only the attacks, but the"High Fat Diet" and physical appearance of some of these firefighters. I think a lot of Doctors would agree with me that,in the physical shape they were in, some of these firefighters would NOT of made it to the 79th floor carrying over 60 lbs of gear. Having said that i now have a greater respect for firefighters and i realize becoming a firefighter is a life altering job. The French have a history of making great documentary\'s and that is what this is, a Great Documentary.....' Label : 1 (pos) 2021-12-01 12:17:32.795514: W tensorflow/core/kernels/data/cache_dataset_ops.cc:768] The calling iterator did not fully read the dataset being cached. In order to avoid unexpected truncation of the dataset, the partially cached contents of the dataset will be discarded. This can happen if you have an input pipeline similar to `dataset.cache().take(k).repeat()`. You should use `dataset.take(k).cache().repeat()` instead.
টেনসরফ্লো হাব থেকে মডেল লোড হচ্ছে
এখানে আপনি টেনসরফ্লো হাব এবং ফাইন-টিউন থেকে কোন BERT মডেলটি লোড করবেন তা বেছে নিতে পারেন। একাধিক BERT মডেল পাওয়া যায়।
- বার্ট-বেজ , Uncased এবং আরও সাত মডেলের মূল বার্ট লেখক দ্বারা মুক্তি প্রশিক্ষিত ওজন সঙ্গে।
- ছোট BERTs একই স্থাপত্য কিন্তু তার চেয়ে কম এবং / অথবা ছোট ট্রান্সফরমার ব্লক, আপনি গতি, আকার এবং মানের মধ্যে tradeoffs এক্সপ্লোর করতে দেয় যা আছে।
- ALBERT : যে স্তর মধ্যে পরামিতি ভাগ করে মডেল আকার (কিন্তু গণনার সময়) হ্রাস করা "একজন লাইট বার্ট" এর চারটি ভিন্ন মাপ।
- বার্ট বিশেষজ্ঞরা : আট মডেল যে সব বার্ট-মূল আর্কিটেকচার আছে কিন্তু বিভিন্ন প্রাক প্রশিক্ষণ ডোমেইনের মধ্যে একটা চয়েস প্রস্তাব, লক্ষ্য কাজে আরো ঘনিষ্ঠভাবে সারিবদ্ধ।
- ইলেকট্রা বার্ট হিসাবে একই স্থাপত্য (তিন বিভিন্ন আকারের) আছে, কিন্তু একটি সেট-আপ একটি discriminator যেমন প্রাক প্রশিক্ষিত পরার যে বর্ণনার অনুরূপ একটি সৃজক adversarial নেটওয়ার্ক (GAN)।
- টকিং-নেতৃবৃন্দ মনোযোগ এবং সুরক্ষতাপূর্ণ GELU [সঙ্গে বার্ট বেস , বড় ] ট্রান্সফরমার স্থাপত্যের কোর দুই উন্নতি হয়েছে।
টেনসরফ্লো হাবের মডেল ডকুমেন্টেশনে গবেষণা সাহিত্যের আরও বিশদ বিবরণ এবং উল্লেখ রয়েছে। উপরের লিঙ্কগুলি অনুসরণ করুন, অথবা এ ক্লিক করুন tfhub.dev
URL টি পরবর্তী সেল সঞ্চালনের পর মুদ্রিত।
পরামর্শ হল একটি ছোট BERT দিয়ে শুরু করা (কম পরামিতি সহ) যেহেতু তারা দ্রুত সূক্ষ্ম-টিউন করে। আপনি যদি একটি ছোট মডেল পছন্দ করেন তবে উচ্চতর নির্ভুলতার সাথে, আলবার্ট আপনার পরবর্তী বিকল্প হতে পারে। আপনি যদি আরও ভালো নির্ভুলতা চান, তাহলে ক্লাসিক BERT মাপ বা ইলেক্ট্রা, টকিং হেডস বা একজন BERT বিশেষজ্ঞের মতো সাম্প্রতিক পরিমার্জনগুলির মধ্যে একটি বেছে নিন।
একপাশে মডেলের নীচের পাওয়া থেকে আছে একাধিক সংস্করণ মডেল যে বৃহত্তর এবং আরও ভাল সঠিকতা উত্পাদ করতে পারেন, কিন্তু তারা খুব ফাইন টিউন একটি একক জিপিইউ করা বড়। আপনি যে করতে হবে সেই বিষয়ে সক্ষম হবে সমাধান আঠা একটি নমনীয় colab উপর বার্ট ব্যবহার কর্ম ।
আপনি নীচের কোডে দেখতে পাবেন যে এই মডেলগুলির যেকোনো একটি চেষ্টা করার জন্য tfhub.dev URL পরিবর্তন করাই যথেষ্ট, কারণ তাদের মধ্যে সমস্ত পার্থক্য TF হাব থেকে সংরক্ষিত মডেলগুলিতে এনক্যাপসুলেট করা হয়েছে৷
সূক্ষ্ম সুর করার জন্য একটি BERT মডেল চয়ন করুন
bert_model_name = 'small_bert/bert_en_uncased_L-4_H-512_A-8'
map_name_to_handle = {
'bert_en_uncased_L-12_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_en_uncased_L-12_H-768_A-12/3',
'bert_en_cased_L-12_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_en_cased_L-12_H-768_A-12/3',
'bert_multi_cased_L-12_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_multi_cased_L-12_H-768_A-12/3',
'small_bert/bert_en_uncased_L-2_H-128_A-2':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-2_H-128_A-2/1',
'small_bert/bert_en_uncased_L-2_H-256_A-4':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-2_H-256_A-4/1',
'small_bert/bert_en_uncased_L-2_H-512_A-8':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-2_H-512_A-8/1',
'small_bert/bert_en_uncased_L-2_H-768_A-12':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-2_H-768_A-12/1',
'small_bert/bert_en_uncased_L-4_H-128_A-2':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-4_H-128_A-2/1',
'small_bert/bert_en_uncased_L-4_H-256_A-4':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-4_H-256_A-4/1',
'small_bert/bert_en_uncased_L-4_H-512_A-8':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-4_H-512_A-8/1',
'small_bert/bert_en_uncased_L-4_H-768_A-12':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-4_H-768_A-12/1',
'small_bert/bert_en_uncased_L-6_H-128_A-2':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-6_H-128_A-2/1',
'small_bert/bert_en_uncased_L-6_H-256_A-4':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-6_H-256_A-4/1',
'small_bert/bert_en_uncased_L-6_H-512_A-8':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-6_H-512_A-8/1',
'small_bert/bert_en_uncased_L-6_H-768_A-12':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-6_H-768_A-12/1',
'small_bert/bert_en_uncased_L-8_H-128_A-2':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-8_H-128_A-2/1',
'small_bert/bert_en_uncased_L-8_H-256_A-4':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-8_H-256_A-4/1',
'small_bert/bert_en_uncased_L-8_H-512_A-8':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-8_H-512_A-8/1',
'small_bert/bert_en_uncased_L-8_H-768_A-12':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-8_H-768_A-12/1',
'small_bert/bert_en_uncased_L-10_H-128_A-2':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-10_H-128_A-2/1',
'small_bert/bert_en_uncased_L-10_H-256_A-4':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-10_H-256_A-4/1',
'small_bert/bert_en_uncased_L-10_H-512_A-8':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-10_H-512_A-8/1',
'small_bert/bert_en_uncased_L-10_H-768_A-12':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-10_H-768_A-12/1',
'small_bert/bert_en_uncased_L-12_H-128_A-2':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-12_H-128_A-2/1',
'small_bert/bert_en_uncased_L-12_H-256_A-4':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-12_H-256_A-4/1',
'small_bert/bert_en_uncased_L-12_H-512_A-8':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-12_H-512_A-8/1',
'small_bert/bert_en_uncased_L-12_H-768_A-12':
'https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-12_H-768_A-12/1',
'albert_en_base':
'https://tfhub.dev/tensorflow/albert_en_base/2',
'electra_small':
'https://tfhub.dev/google/electra_small/2',
'electra_base':
'https://tfhub.dev/google/electra_base/2',
'experts_pubmed':
'https://tfhub.dev/google/experts/bert/pubmed/2',
'experts_wiki_books':
'https://tfhub.dev/google/experts/bert/wiki_books/2',
'talking-heads_base':
'https://tfhub.dev/tensorflow/talkheads_ggelu_bert_en_base/1',
}
map_model_to_preprocess = {
'bert_en_uncased_L-12_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'bert_en_cased_L-12_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_en_cased_preprocess/3',
'small_bert/bert_en_uncased_L-2_H-128_A-2':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-2_H-256_A-4':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-2_H-512_A-8':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-2_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-4_H-128_A-2':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-4_H-256_A-4':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-4_H-512_A-8':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-4_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-6_H-128_A-2':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-6_H-256_A-4':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-6_H-512_A-8':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-6_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-8_H-128_A-2':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-8_H-256_A-4':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-8_H-512_A-8':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-8_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-10_H-128_A-2':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-10_H-256_A-4':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-10_H-512_A-8':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-10_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-12_H-128_A-2':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-12_H-256_A-4':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-12_H-512_A-8':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'small_bert/bert_en_uncased_L-12_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'bert_multi_cased_L-12_H-768_A-12':
'https://tfhub.dev/tensorflow/bert_multi_cased_preprocess/3',
'albert_en_base':
'https://tfhub.dev/tensorflow/albert_en_preprocess/3',
'electra_small':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'electra_base':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'experts_pubmed':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'experts_wiki_books':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
'talking-heads_base':
'https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3',
}
tfhub_handle_encoder = map_name_to_handle[bert_model_name]
tfhub_handle_preprocess = map_model_to_preprocess[bert_model_name]
print(f'BERT model selected : {tfhub_handle_encoder}')
print(f'Preprocess model auto-selected: {tfhub_handle_preprocess}')
BERT model selected : https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-4_H-512_A-8/1 Preprocess model auto-selected: https://tfhub.dev/tensorflow/bert_en_uncased_preprocess/3
প্রিপ্রসেসিং মডেল
পাঠ্য ইনপুটগুলিকে সংখ্যাসূচক টোকেন আইডিতে রূপান্তরিত করতে হবে এবং BERT-তে ইনপুট করার আগে কয়েকটি টেনসরে সাজানো দরকার। TensorFlow Hub উপরে আলোচিত প্রতিটি BERT মডেলের জন্য একটি ম্যাচিং প্রিপ্রসেসিং মডেল প্রদান করে, যা TF.text লাইব্রেরি থেকে TF ops ব্যবহার করে এই রূপান্তরটি বাস্তবায়ন করে। টেক্সট প্রিপ্রসেস করতে আপনার টেনসরফ্লো মডেলের বাইরে বিশুদ্ধ পাইথন কোড চালানোর প্রয়োজন নেই।
প্রিপ্রসেসিং মডেলটি অবশ্যই BERT মডেলের ডকুমেন্টেশন দ্বারা উল্লেখ করা একটি হতে হবে, যা আপনি উপরে মুদ্রিত URL এ পড়তে পারেন। উপরের ড্রপ-ডাউন থেকে BERT মডেলের জন্য, প্রিপ্রসেসিং মডেলটি স্বয়ংক্রিয়ভাবে নির্বাচিত হয়।
bert_preprocess_model = hub.KerasLayer(tfhub_handle_preprocess)
আসুন কিছু পাঠ্যের প্রিপ্রসেসিং মডেলটি চেষ্টা করি এবং আউটপুটটি দেখি:
text_test = ['this is such an amazing movie!']
text_preprocessed = bert_preprocess_model(text_test)
print(f'Keys : {list(text_preprocessed.keys())}')
print(f'Shape : {text_preprocessed["input_word_ids"].shape}')
print(f'Word Ids : {text_preprocessed["input_word_ids"][0, :12]}')
print(f'Input Mask : {text_preprocessed["input_mask"][0, :12]}')
print(f'Type Ids : {text_preprocessed["input_type_ids"][0, :12]}')
Keys : ['input_word_ids', 'input_mask', 'input_type_ids'] Shape : (1, 128) Word Ids : [ 101 2023 2003 2107 2019 6429 3185 999 102 0 0 0] Input Mask : [1 1 1 1 1 1 1 1 1 0 0 0] Type Ids : [0 0 0 0 0 0 0 0 0 0 0 0]
যেহেতু আপনি দেখতে পারেন, এখন আপনি প্রাক-প্রক্রিয়াকরণ করে একটি বার্ট মডেল (ব্যবহার করেন 3 আউটপুট আছে input_words_id
, input_mask
এবং input_type_ids
)।
আরও কিছু গুরুত্বপূর্ণ পয়েন্ট:
- ইনপুটটি 128 টোকেনে কাটা হয়েছে। টোকেন সংখ্যা কাস্টমাইজ করা যায়, এবং আপনি আরও বিশদের দেখতে পারেন একটি নমনীয় colab উপর বার্ট ব্যবহার সমাধান আঠালো কর্ম ।
-
input_type_ids
শুধুমাত্র একটি মান (0) আছে কারণ এই একটি বাক্য ইনপুট হয়। একাধিক বাক্য ইনপুটের জন্য, প্রতিটি ইনপুটের জন্য এটির একটি সংখ্যা থাকবে।
যেহেতু এই টেক্সট প্রিপ্রসেসরটি একটি TensorFlow মডেল, এটি সরাসরি আপনার মডেলে অন্তর্ভুক্ত করা যেতে পারে।
BERT মডেল ব্যবহার করে
আপনার নিজের মডেলে BERT স্থাপন করার আগে, এর আউটপুটগুলি একবার দেখে নেওয়া যাক। আপনি এটি টিএফ হাব থেকে লোড করবেন এবং ফিরে আসা মানগুলি দেখতে পাবেন।
bert_model = hub.KerasLayer(tfhub_handle_encoder)
bert_results = bert_model(text_preprocessed)
print(f'Loaded BERT: {tfhub_handle_encoder}')
print(f'Pooled Outputs Shape:{bert_results["pooled_output"].shape}')
print(f'Pooled Outputs Values:{bert_results["pooled_output"][0, :12]}')
print(f'Sequence Outputs Shape:{bert_results["sequence_output"].shape}')
print(f'Sequence Outputs Values:{bert_results["sequence_output"][0, :12]}')
Loaded BERT: https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-4_H-512_A-8/1 Pooled Outputs Shape:(1, 512) Pooled Outputs Values:[ 0.76262873 0.99280983 -0.1861186 0.36673835 0.15233682 0.65504444 0.9681154 -0.9486272 0.00216158 -0.9877732 0.0684272 -0.9763061 ] Sequence Outputs Shape:(1, 128, 512) Sequence Outputs Values:[[-0.28946388 0.3432126 0.33231565 ... 0.21300787 0.7102078 -0.05771166] [-0.28742015 0.31981024 -0.2301858 ... 0.58455074 -0.21329722 0.7269209 ] [-0.66157013 0.6887685 -0.87432927 ... 0.10877253 -0.26173282 0.47855264] ... [-0.2256118 -0.28925604 -0.07064401 ... 0.4756601 0.8327715 0.40025353] [-0.29824278 -0.27473143 -0.05450511 ... 0.48849759 1.0955356 0.18163344] [-0.44378197 0.00930723 0.07223766 ... 0.1729009 1.1833246 0.07897988]]
বার্ট মডেলের 3 গুরুত্বপূর্ণ কী এর মাধ্যমে একটি মানচিত্র ফিরে pooled_output
, sequence_output
, encoder_outputs
:
-
pooled_output
সামগ্রিকভাবে প্রতিটি ইনপুট ক্রম প্রতিনিধিত্ব করে। আকৃতি হয়[batch_size, H]
। আপনি এটিকে সম্পূর্ণ মুভি পর্যালোচনার জন্য একটি এম্বেডিং হিসাবে ভাবতে পারেন। -
sequence_output
প্রতিটি ইনপুট প্রেক্ষাপটে টোকেনটি প্রতিনিধিত্ব করে। আকৃতি হয়[batch_size, seq_length, H]
। আপনি এটিকে মুভি পর্যালোচনাতে প্রতিটি টোকেনের জন্য একটি প্রাসঙ্গিক এম্বেডিং হিসাবে ভাবতে পারেন। -
encoder_outputs
এর মধ্যবর্তী সক্রিয়করণব্যবস্থা হয়L
ট্রান্সফরমার ব্লক।outputs["encoder_outputs"][i]
আকৃতি একটি টেন্সর হয়[batch_size, seq_length, 1024]
আমি-তম ট্রান্সফরমার ব্লক আউটপুট সঙ্গে, জন্য0 <= i < L
। তালিকার সর্বশেষ মান সমানsequence_output
।
ফাইন টিউনিং জন্য আপনি ব্যবহার করতে যাচ্ছি pooled_output
অ্যারে।
আপনার মডেল সংজ্ঞায়িত করুন
আপনি প্রিপ্রসেসিং মডেল, নির্বাচিত BERT মডেল, একটি ঘন এবং একটি ড্রপআউট স্তর সহ একটি খুব সাধারণ সূক্ষ্ম-টিউনড মডেল তৈরি করবেন।
def build_classifier_model():
text_input = tf.keras.layers.Input(shape=(), dtype=tf.string, name='text')
preprocessing_layer = hub.KerasLayer(tfhub_handle_preprocess, name='preprocessing')
encoder_inputs = preprocessing_layer(text_input)
encoder = hub.KerasLayer(tfhub_handle_encoder, trainable=True, name='BERT_encoder')
outputs = encoder(encoder_inputs)
net = outputs['pooled_output']
net = tf.keras.layers.Dropout(0.1)(net)
net = tf.keras.layers.Dense(1, activation=None, name='classifier')(net)
return tf.keras.Model(text_input, net)
আসুন পরীক্ষা করে দেখি যে মডেলটি প্রিপ্রসেসিং মডেলের আউটপুট দিয়ে চলে।
classifier_model = build_classifier_model()
bert_raw_result = classifier_model(tf.constant(text_test))
print(tf.sigmoid(bert_raw_result))
tf.Tensor([[0.6749899]], shape=(1, 1), dtype=float32)
আউটপুট অর্থহীন, অবশ্যই, কারণ মডেলটি এখনও প্রশিক্ষিত হয়নি।
আসুন মডেলটির গঠনটি দেখে নেওয়া যাক।
tf.keras.utils.plot_model(classifier_model)
মডেল প্রশিক্ষণ
প্রিপ্রসেসিং মডিউল, BERT এনকোডার, ডেটা এবং ক্লাসিফায়ার সহ একটি মডেলকে প্রশিক্ষণ দেওয়ার জন্য আপনার কাছে এখন সমস্ত টুকরো রয়েছে।
ক্ষতি ফাংশন
যেহেতু এই একটি বাইনারি শ্রেণীবিন্যাস সমস্যা এবং মডেল একটি সম্ভাব্যতা (ক একক ইউনিট স্তর) আউটপুট, আপনি ব্যবহার করব losses.BinaryCrossentropy
ক্ষতি ফাংশন।
loss = tf.keras.losses.BinaryCrossentropy(from_logits=True)
metrics = tf.metrics.BinaryAccuracy()
অপ্টিমাইজার
ফাইন-টিউনিং-এর জন্য, আসুন একই অপ্টিমাইজার ব্যবহার করি যার সাথে BERT মূলত প্রশিক্ষিত হয়েছিল: "অ্যাডাপ্টিভ মোমেন্টস" (অ্যাডাম)। এই অপটিমাইজার ভবিষ্যদ্বাণী ক্ষতি ছোট এবং ওজন ক্ষয় (মুহূর্ত ব্যবহার করছেন না), যা নামেও পরিচিত হয় নিয়মিতকরণ করে AdamW ।
লার্নিং হার (জন্য init_lr
), আপনি একই সময়সূচী ব্যবহার বার্ট প্রাক প্রশিক্ষণ হবে: একটি ধারণাগত প্রাথমিক শিক্ষা হারের রৈখিক ক্ষয়, ওভার প্রশিক্ষণ পদক্ষেপ (প্রথম 10% একটি রৈখিক ওয়ার্ম আপ ফেজ প্রিফিক্স num_warmup_steps
)। BERT কাগজের সাথে সামঞ্জস্য রেখে, ফাইন-টিউনিংয়ের জন্য প্রাথমিক শিক্ষার হার ছোট (5e-5, 3e-5, 2e-5-এর সেরা)।
epochs = 5
steps_per_epoch = tf.data.experimental.cardinality(train_ds).numpy()
num_train_steps = steps_per_epoch * epochs
num_warmup_steps = int(0.1*num_train_steps)
init_lr = 3e-5
optimizer = optimization.create_optimizer(init_lr=init_lr,
num_train_steps=num_train_steps,
num_warmup_steps=num_warmup_steps,
optimizer_type='adamw')
BERT মডেল এবং প্রশিক্ষণ লোড করা হচ্ছে
ব্যবহার classifier_model
আপনি আগে তৈরি করে থাকে, ক্ষতি, মেট্রিক এবং অপটিমাইজার সঙ্গে মডেল কম্পাইল করতে পারেন।
classifier_model.compile(optimizer=optimizer,
loss=loss,
metrics=metrics)
print(f'Training model with {tfhub_handle_encoder}')
history = classifier_model.fit(x=train_ds,
validation_data=val_ds,
epochs=epochs)
Training model with https://tfhub.dev/tensorflow/small_bert/bert_en_uncased_L-4_H-512_A-8/1 Epoch 1/5 625/625 [==============================] - 91s 138ms/step - loss: 0.4776 - binary_accuracy: 0.7513 - val_loss: 0.3791 - val_binary_accuracy: 0.8380 Epoch 2/5 625/625 [==============================] - 85s 136ms/step - loss: 0.3266 - binary_accuracy: 0.8547 - val_loss: 0.3659 - val_binary_accuracy: 0.8486 Epoch 3/5 625/625 [==============================] - 86s 138ms/step - loss: 0.2521 - binary_accuracy: 0.8928 - val_loss: 0.3975 - val_binary_accuracy: 0.8518 Epoch 4/5 625/625 [==============================] - 86s 137ms/step - loss: 0.1910 - binary_accuracy: 0.9269 - val_loss: 0.4180 - val_binary_accuracy: 0.8522 Epoch 5/5 625/625 [==============================] - 86s 137ms/step - loss: 0.1509 - binary_accuracy: 0.9433 - val_loss: 0.4641 - val_binary_accuracy: 0.8522
মডেল মূল্যায়ন
আসুন দেখি মডেলটি কেমন করে। দুটি মান ফেরত দেওয়া হবে। ক্ষতি (একটি সংখ্যা যা ত্রুটির প্রতিনিধিত্ব করে, নিম্ন মানগুলি ভাল), এবং নির্ভুলতা।
loss, accuracy = classifier_model.evaluate(test_ds)
print(f'Loss: {loss}')
print(f'Accuracy: {accuracy}')
782/782 [==============================] - 61s 78ms/step - loss: 0.4495 - binary_accuracy: 0.8554 Loss: 0.4494614601135254 Accuracy: 0.8553599715232849
সময়ের সাথে সাথে সঠিকতা এবং ক্ষতি প্লট করুন
উপর ভিত্তি করে History
বস্তু দ্বারা ফিরে model.fit()
আপনি তুলনা করার জন্য প্রশিক্ষণ এবং বৈধতা হারানোর পরিকল্পনা করতে পারেন, সেইসাথে প্রশিক্ষণ এবং যাচাইকরণের সঠিকতা:
history_dict = history.history
print(history_dict.keys())
acc = history_dict['binary_accuracy']
val_acc = history_dict['val_binary_accuracy']
loss = history_dict['loss']
val_loss = history_dict['val_loss']
epochs = range(1, len(acc) + 1)
fig = plt.figure(figsize=(10, 6))
fig.tight_layout()
plt.subplot(2, 1, 1)
# r is for "solid red line"
plt.plot(epochs, loss, 'r', label='Training loss')
# b is for "solid blue line"
plt.plot(epochs, val_loss, 'b', label='Validation loss')
plt.title('Training and validation loss')
# plt.xlabel('Epochs')
plt.ylabel('Loss')
plt.legend()
plt.subplot(2, 1, 2)
plt.plot(epochs, acc, 'r', label='Training acc')
plt.plot(epochs, val_acc, 'b', label='Validation acc')
plt.title('Training and validation accuracy')
plt.xlabel('Epochs')
plt.ylabel('Accuracy')
plt.legend(loc='lower right')
dict_keys(['loss', 'binary_accuracy', 'val_loss', 'val_binary_accuracy']) <matplotlib.legend.Legend at 0x7fee7cdb4450>
এই প্লটে, লাল রেখাগুলি প্রশিক্ষণের ক্ষতি এবং নির্ভুলতার প্রতিনিধিত্ব করে এবং নীল রেখাগুলি হল বৈধতা ক্ষতি এবং নির্ভুলতা।
অনুমান জন্য রপ্তানি
এখন আপনি পরবর্তীতে ব্যবহারের জন্য আপনার সূক্ষ্ম টিউন করা মডেলটি সংরক্ষণ করুন।
dataset_name = 'imdb'
saved_model_path = './{}_bert'.format(dataset_name.replace('/', '_'))
classifier_model.save(saved_model_path, include_optimizer=False)
2021-12-01 12:26:06.207608: W tensorflow/python/util/util.cc:368] Sets are not currently considered sequences, but this may change in the future, so consider avoiding using them. WARNING:absl:Found untraced functions such as restored_function_body, restored_function_body, restored_function_body, restored_function_body, restored_function_body while saving (showing 5 of 310). These functions will not be directly callable after loading.
আসুন মডেলটি পুনরায় লোড করি, যাতে আপনি এখনও মেমরিতে থাকা মডেলটির পাশাপাশি এটি চেষ্টা করতে পারেন।
reloaded_model = tf.saved_model.load(saved_model_path)
এখানে আপনি যে কোনো বাক্যে আপনার মডেল পরীক্ষা করতে পারেন, শুধু নিচের ভেরিয়েবলের উদাহরণ যোগ করুন।
def print_my_examples(inputs, results):
result_for_printing = \
[f'input: {inputs[i]:<30} : score: {results[i][0]:.6f}'
for i in range(len(inputs))]
print(*result_for_printing, sep='\n')
print()
examples = [
'this is such an amazing movie!', # this is the same sentence tried earlier
'The movie was great!',
'The movie was meh.',
'The movie was okish.',
'The movie was terrible...'
]
reloaded_results = tf.sigmoid(reloaded_model(tf.constant(examples)))
original_results = tf.sigmoid(classifier_model(tf.constant(examples)))
print('Results from the saved model:')
print_my_examples(examples, reloaded_results)
print('Results from the model in memory:')
print_my_examples(examples, original_results)
Results from the saved model: input: this is such an amazing movie! : score: 0.999521 input: The movie was great! : score: 0.997015 input: The movie was meh. : score: 0.988535 input: The movie was okish. : score: 0.079138 input: The movie was terrible... : score: 0.001622 Results from the model in memory: input: this is such an amazing movie! : score: 0.999521 input: The movie was great! : score: 0.997015 input: The movie was meh. : score: 0.988535 input: The movie was okish. : score: 0.079138 input: The movie was terrible... : score: 0.001622
আপনি আপনার মডেল ব্যবহার করতে চান তাহলে মেমরি ভজনা , মনে রাখবেন যে এটা তার নামে স্বাক্ষর একজনের কাছ থেকে আপনার SavedModel কল হবে। পাইথনে, আপনি তাদের নিম্নলিখিত হিসাবে পরীক্ষা করতে পারেন:
serving_results = reloaded_model \
.signatures['serving_default'](tf.constant(examples))
serving_results = tf.sigmoid(serving_results['classifier'])
print_my_examples(examples, serving_results)
input: this is such an amazing movie! : score: 0.999521 input: The movie was great! : score: 0.997015 input: The movie was meh. : score: 0.988535 input: The movie was okish. : score: 0.079138 input: The movie was terrible... : score: 0.001622
পরবর্তী পদক্ষেপ
একটি পরবর্তী ধাপে হিসাবে, আপনি চেষ্টা করে দেখতে পারেন একটি নমনীয় টিউটোরিয়াল উপর বার্ট ব্যবহার আঠালো কর্ম সমাধান , যা একটি নমনীয় এবং কিভাবে আপনি একাধিক ইনপুট সঙ্গে কাজ করার শো চলন খুব বেশি।