`ধরা (…) {নিক্ষেপ; bad `একটি খারাপ অভ্যাস?


74

যদিও আমি সম্মত হই যে ... পুনর্বিবেচনা ছাড়াই ধরা সত্যই ভুল, তবুও আমি বিশ্বাস করি যে এইরকম কনস্ট্রাক্ট ব্যবহার করা:

try
{
  // Stuff
}
catch (...)
{
  // Some cleanup
  throw;
}

RAII প্রযোজ্য নয় এমন ক্ষেত্রে গ্রহণযোগ্য । (দয়া করে, জিজ্ঞাসা করবেন না ... আমার সংস্থার প্রত্যেকেই অবজেক্ট-ভিত্তিক প্রোগ্রামিং পছন্দ করে না এবং আরআইআইআইকে প্রায়শই "অকেজো বিদ্যালয়ের জিনিস" হিসাবে দেখা যায় না ...)

আমার সহকর্মীরা বলেছেন যে আপনার সর্বদা জানা উচিত যে কোন ব্যতিক্রমগুলি নিক্ষেপ করা হবে এবং আপনি সর্বদা এই জাতীয় নির্মাণ ব্যবহার করতে পারেন:

try
{
  // Stuff
}
catch (exception_type1&)
{
  // Some cleanup
  throw;
}
catch (exception_type2&)
{
  // Some cleanup
  throw;
}
catch (exception_type3&)
{
  // Some cleanup
  throw;
}

এই পরিস্থিতিতে একটি ভাল প্রশংসিত ভাল অনুশীলন আছে?


3
@ পাব্বি: নিশ্চিত না এটি হুবহু একই প্রশ্ন। লিঙ্কিত প্রশ্নটি " ...আমার কি ধরা উচিত" সম্পর্কে আরও বেশি, যখন আমার প্রশ্নটি "আমাকে আরও ভাল করে ধরা উচিত ...বা <specific exception>পুনর্নির্মাণের আগে"

53
এটি বলার জন্য দুঃখিত, তবে RAII ছাড়াই সি ++ সি ++ নয়।
ফ্রেডওভারফ্লো

46
সুতরাং আপনার গরু-কর্মীরা কোনও নির্দিষ্ট সমস্যার মোকাবিলা করার জন্য যে কৌশলটি আবিষ্কার করেছিলেন তা খারিজ করে এবং তারপরে কোন নিকৃষ্ট বিকল্পটি ব্যবহার করা উচিত তা নিয়ে উদ্বেগজনক? দুঃখের সাথে বলতে চাই, তবে এটি নির্বোধ বলে মনে হচ্ছে , আমি এটি যেভাবেই দেখছি।
এসবিআই

11
"ধরা ... পুনর্বিবেচনা ছাড়া সত্যই ভুল" - আপনি ভুল করেছেন। ইন main, খুব catch(...) { return EXIT_FAILURE; }ভাল কোডে থাকতে পারে যা কোনও ডিবাগারের অধীনে চলছে না। আপনি যদি ধরেন না, তবে স্ট্যাকটি আনউন্ডাউন্ড নাও হতে পারে। এটি কেবল তখনই যখন আপনার ডিবাগারটি অপ্রকাশিত ব্যতিক্রমগুলি সনাক্ত করে যা আপনি তাদের ছেড়ে যেতে চান main
স্টিভ জেসপ

3
... সুতরাং এটি "প্রোগ্রামিং ত্রুটি" হলেও এটি প্রয়োজনীয়ভাবে অনুসরণ করে না যে আপনি এটি সম্পর্কে জানতে চান না। যাইহোক, আপনার সহকর্মীরা ভাল সফ্টওয়্যার পেশাদার নন, সুতরাং এসবিআই যেমন বলেছিল যে পরিস্থিতিটি শুরু করার পক্ষে ক্রমশঃ দুর্বল পরিস্থিতিটি কীভাবে মোকাবেলা করা যায় তার বিষয়ে কথা বলা খুব কঠিন।
স্টিভ জেসপ

উত্তর:


196

আমার সহকর্মীরা বলেছেন যে আপনার ব্যতিক্রমগুলি নিক্ষেপ করা উচিত তা সর্বদা আপনার জানা উচিত [...]

আপনার সহকর্মী, আমি এটি বলতে ঘৃণা করি, স্পষ্টত কখনও সাধারণ উদ্দেশ্যে লাইব্রেরিগুলিতে কাজ করেনি।

কীভাবে পৃথিবীতে এমন কোনও শ্রেণি std::vectorএমনকি কপিরাইট নির্মাতারা কী নিক্ষেপ করবে তা জানার ভান করতে পারে, যখন এখনও ব্যতিক্রম সুরক্ষার গ্যারান্টি দিয়ে থাকে?

আপনি যদি সর্বদা জানতেন যে সংকলনকালে কলি কী করবে, তবে বহুত্ববাদ ব্যর্থ হবে! কখনও কখনও পুরো লক্ষ্যটি হ'ল নিম্ন স্তরে যা ঘটে তা বিমূর্ত করা, যাতে আপনি বিশেষত কী জানতে চাইছেন তা জানতে চান না !


32
আসলে, এমনকি যদি তারা জানত যে ব্যতিক্রমগুলি ছুঁড়ে দেওয়া হবে। এই কোড সদৃশ এর উদ্দেশ্য কি? হ্যান্ডলিংয়ের ভিন্নতা না থাকলে আমি আপনার জ্ঞান প্রদর্শন করার ব্যতিক্রমগুলি গণনা করার কোনও অর্থ দেখতে পাচ্ছি না।
মাইকেল ক্রেলিন - হ্যাকার

3
@ মাইকেল ক্রেলিন-হ্যাকার: তাও। এছাড়াও, এটিকে যুক্ত করুন যে তারা ব্যতিক্রমের স্পেসিফিকেশনগুলি অবমূল্যায়ন করেছেন কারণ কোডে সমস্ত সম্ভাব্য ব্যতিক্রমগুলি তালিকাভুক্তকরণ পরে বাগগুলি তৈরি করার ঝোঁক রেখেছিল ... এটি এখন পর্যন্ত সবচেয়ে খারাপ ধারণা।
মেহেরদাবাদ

4
দরকারী এবং সুবিধাজনক কৌশলটি "অকেজো স্কুলের স্টাফ" হিসাবে দেখার সাথে মিলিত হওয়ার সাথে সাথে এমন মনোভাবের মূল কারণ কী হতে পারে এবং তা আমাকে বিরক্ত করে। তবে ভাল ...
মাইকেল ক্রেলিন - হ্যাকার

1
+1, সমস্ত সম্ভাব্য বিকল্পগুলির গণনা হ'ল ভবিষ্যতের ব্যর্থতার জন্য একটি দুর্দান্ত রেসিপি, কেন পৃথিবীতে কেউ এই কাজটি করতে পছন্দ করবে ...?
littleadv

2
চমৎকার উত্তর. এটি সম্ভবত উল্লেখ করে উপকৃত হতে পারে যে কোনও সংকলক যেটিকে সমর্থন করতে হবে তা যদি এক্স এক্স অঞ্চলে বাগ থাকে তবে এক্স অঞ্চল থেকে কার্যকারিতা ব্যবহার করা স্মার্ট নয়, অন্তত সরাসরি ব্যবহার না করা। উদাহরণস্বরূপ, সংস্থা সম্পর্কে তথ্য দেওয়া, আমি অবাক হব না যদি তারা ভিজ্যুয়াল সি ++ 6.0 ব্যবহার করে, যার এই অঞ্চলে কিছু সিলিব্যাগ ছিল (যেমন ব্যতিক্রমী অবজেক্ট ধ্বংসকারীদের দু'বার বলা হয়) - সেই প্রাথমিক বাগগুলির কিছু ছোট বংশধর বেঁচে থাকতে পেরেছে এই দিনটি, তবে প্রকাশের জন্য সতর্কতার প্রয়োজন।
আলফ পি স্টেইনবাচ

44

আপনি যেটিকে ধরা পড়েছেন বলে মনে হচ্ছে তা হ'ল কারও কেকের কাছে থাকার চেষ্টা করে এবং এটিও খাওয়ার চেষ্টা করার নির্দিষ্ট নরক।

আরআইআইআই এবং ব্যতিক্রমগুলি হাতে হাতে ডিজাইন করা হয়েছে। RAII যার দ্বারা আপনি না আছে অনেক লিখতে catch(...)পরিষ্করণ করতে বিবৃতি। এটি অবশ্যই স্বয়ংক্রিয়ভাবে ঘটবে। এবং ব্যতিক্রমগুলি কেবলমাত্র RAII অবজেক্টের সাথে কাজ করার একমাত্র উপায়, কারণ নির্মাতারা কেবল সফল বা নিক্ষেপ করতে পারে (বা বস্তুটিকে একটি ত্রুটি অবস্থায় ফেলে দিতে পারে, তবে কে তা চায়?)।

একটি catchবিবৃতি দুটি জিনিসের মধ্যে একটি করতে পারে: একটি ত্রুটি বা ব্যতিক্রমী পরিস্থিতি পরিচালনা করুন, বা ক্লিনআপ কাজ করুন। কখনও কখনও এটি উভয়ই করে তবে প্রতিটি catchবিবৃতি এগুলির অন্তত একটি করতে উপস্থিত থাকে।

catch(...)সঠিক ব্যতিক্রম হ্যান্ডলিং করতে অক্ষম। ব্যতিক্রম কী তা আপনি জানেন না; আপনি ব্যতিক্রম সম্পর্কে তথ্য পেতে পারেন না। একটি নির্দিষ্ট কোড ব্লকের মধ্যে কিছু দ্বারা ব্যতিক্রম ছুঁড়ে ফেলেছে তা ব্যতীত আপনার কাছে একেবারেই কোনও তথ্য নেই । এই জাতীয় ব্লকটিতে আপনি কেবল বৈধ কাজটি করতে পারেন তা হল ক্লিনআপ করা। এবং এর অর্থ ক্লিনআপ শেষে ব্যতিক্রমটি পুনরায় নিক্ষেপ করা।

ব্যতিক্রম পরিচালনার ক্ষেত্রে আরআইআই আপনাকে যা দেয় তা হ'ল ফ্রি ক্লিনআপ। যদি সমস্ত কিছু RAII যথাযথভাবে encapsulated হয়, তবে সবকিছু সঠিকভাবে পরিষ্কার করা হবে up catchপরিষ্কার করার জন্য আপনার আর বিবৃতি দেওয়ার দরকার নেই । কোন ক্ষেত্রে catch(...)বিবৃতি লেখার কোনও কারণ নেই ।

সুতরাং আমি সম্মত হবো যে catch(...)বেশিরভাগই অশুভ ... অস্থায়ীভাবে

এই বিধানটি আরআইআইয়ের যথাযথ ব্যবহার হচ্ছে। এটা ছাড়া হওয়ায়, প্রয়োজন নির্দিষ্ট পরিষ্করণ কাজ করতে সক্ষম হবে। এর আশেপাশে কোনও লাভ নেই; আপনি ক্লিনআপ কাজ করতে সক্ষম হতে হবে। আপনাকে এটি নিশ্চিত করতে সক্ষম হতে হবে যে একটি ব্যতিক্রম ছুঁড়ে দেওয়া কোডটি যুক্তিসঙ্গত অবস্থায় ফেলে দেবে। এবং catch(...)এটি করার একটি গুরুত্বপূর্ণ হাতিয়ার।

অপরটি ছাড়া আপনার থাকতে পারে না। আপনি এটি বলতে পারবেন না যে উভয়ই আরআইআই এবং catch(...) খারাপ। এর মধ্যে আপনার অন্তত একটি প্রয়োজন; অন্যথায়, আপনি নিরাপদ ব্যতিক্রম না।

অবশ্যই, এর একটি বৈধ-যদিও-বিরল ব্যবহার catch(...)যা এমনকি আরআইআই নিষিদ্ধ করতে পারে না: exception_ptrঅন্য কারও কাছে ফরোয়ার্ড পাওয়ার জন্য। সাধারণত একটি promise/futureবা অনুরূপ ইন্টারফেসের মাধ্যমে ।

আমার সহকর্মীরা বলেছেন যে আপনার সর্বদা জানা উচিত যে কোন ব্যতিক্রমগুলি নিক্ষেপ করা হবে এবং আপনি সর্বদা এই জাতীয় নির্মাণ ব্যবহার করতে পারেন:

আপনার সহকর্মী একজন নির্বোধ (বা কেবল ভয়ঙ্করভাবে অজ্ঞ)। আপনার লিখিতকরণের পরামর্শ দেওয়ার জন্য তিনি কতটা অনুলিপি-পেস্ট কোডের কারণে তা অবিলম্বে স্পষ্ট হওয়া উচিত। সেই ধরা বিবৃতি প্রত্যেকের জন্য পরিষ্করণ হতে হবে ঠিক একই । এটি একটি রক্ষণাবেক্ষণ দুঃস্বপ্ন, পাঠযোগ্যতার উল্লেখ না করা।

সংক্ষেপে: এই সমস্যাটিই আরএআইআই সমাধান করার জন্য তৈরি করা হয়েছিল (এটি অন্যান্য সমস্যা সমাধান করে না এমন নয়)।

এই ধারণাটি সম্পর্কে আমাকে যা বিভ্রান্ত করে তা হ'ল বেশিরভাগ লোকেরা যেভাবে যুক্তি দেয় যে রাইআইআই খারাপ এটির পিছনে সাধারণত wards সাধারণত, যুক্তিটিতে যায় "আরএআইআইটি খারাপ কারণ আপনাকে কনস্ট্রাক্টর ব্যর্থতার সংকেত দিতে ব্যতিক্রমগুলি ব্যবহার করতে হবে But তবে আপনি ব্যতিক্রমগুলি ছুঁড়তে পারবেন না, কারণ এটি নিরাপদ নয় এবং catchসবকিছু পরিষ্কার করার জন্য আপনাকে প্রচুর বিবৃতি দিতে হবে।" যা একটি ভাঙা যুক্তি কারণ RAII যে সমস্যাটি RAII এর অভাব সৃষ্টি করে তা সমাধান করে।

সম্ভবত আরও বেশি, তিনি আরএআইআইয়ের বিপক্ষে কারণ এটি বিবরণ গোপন করে। ডিস্ট্রাক্টর কলগুলি স্বয়ংক্রিয় ভেরিয়েবলগুলিতে তত্ক্ষণাত দৃশ্যমান হয় না। সুতরাং আপনি এমন কোড পান যা পুরোপুরি কল করে called কিছু প্রোগ্রামার সত্যই তা ঘৃণা করে। স্পষ্টতই, যেখানে তারা মনে করেন যে 3 টি catchস্টেটমেন্ট রয়েছে তারা সকলেই কপি-পেস্ট কোডের সাথে একই জিনিসটি করা একটি ভাল ধারণা।


2
দেখে মনে হচ্ছে আপনি এমন কোড লেখেন নি যা শক্তিশালী ব্যতিক্রমী সুরক্ষা গ্যারান্টি সরবরাহ করে। RAII প্রাথমিক গ্যারান্টি সরবরাহ করতে সহায়তা করে । তবে দৃ strong় গ্যারান্টি সরবরাহ করার জন্য, আপনাকে ফাংশন বলার আগে সিস্টেমটিকে সেই অবস্থায় ফিরিয়ে আনার জন্য কিছু ক্রিয়াকলাপ পূর্বাবস্থায় ফিরিয়ে আনতে হবে। বেসিক গ্যারান্টি ক্লিনআপ , দৃ strong গ্যারান্টি রোলব্যাক । রোলব্যাক করা ফাংশন নির্দিষ্ট। সুতরাং আপনি এটিকে "আরআইআইআই" এ রাখতে পারবেন না। এবং তখনই যখন ক্যাচ-অল ব্লকটি সহজ হয়ে যায়। আপনি যদি দৃ strong় গ্যারান্টি সহ কোড লিখেন তবে আপনি অনেক বেশি ক্যাচ- ব্যবহার করেন ।
anton_rh

@ অ্যান্টন_আরহ: সম্ভবত, তবে সেই ক্ষেত্রেও, সমস্ত বক্তব্যই শেষ রোধের হাতিয়ার । পছন্দসই সরঞ্জামটি হ'ল এমন কিছু করা যা আপনি যে কোনও রাষ্ট্র পরিবর্তনের আগে ছুঁড়ে ফেলেন যা আপনাকে ব্যতিক্রম করতে হবে। স্পষ্টতই আপনি সব ক্ষেত্রে যেভাবে সবকিছু বাস্তবায়ন করতে পারবেন না, তবে দৃ the় ব্যতিক্রম গ্যারান্টিটি পাওয়ার এটিই আদর্শ উপায়।
নিকোল বোলাস

14

দুটি মন্তব্য, সত্যিই। প্রথমটি হ'ল আদর্শ পৃথিবীতে থাকাকালীন সর্বদা আপনার জানা উচিত যে ব্যতিক্রমগুলি কীভাবে ছুঁড়ে ফেলা হতে পারে, বাস্তবে আপনি যদি তৃতীয় পক্ষের লাইব্রেরিগুলি নিয়ে কাজ করছেন বা মাইক্রোসফ্ট সংকলক দিয়ে সংকলন করছেন, আপনি তা করবেন না। আরও মুল বিষয়; এমনকি যদি আপনি সম্ভাব্য ব্যতিক্রমগুলি সম্পর্কে সঠিকভাবে জানেন তবে কী এখানে প্রাসঙ্গিক? এমনকি এর catch (...)চেয়ে catch ( std::exception const& )সম্ভাব্য সমস্ত ব্যতিক্রম থেকে উদ্ভূত ধারণাটি প্রকাশের চেয়ে অভিপ্রায়টিকে আরও ভালভাবে প্রকাশ করেstd::exception(যা আদর্শ বিশ্বের ক্ষেত্রে হবে)। বেশ কয়েকটি ক্যাচ ব্লক ব্যবহার করার ক্ষেত্রে, যদি সমস্ত ব্যাতিক্রমের কোনও সাধারণ ভিত্তি না থাকে: এটি নিখরচায় অবজ্ঞা এবং একটি রক্ষণাবেক্ষণ দুঃস্বপ্ন। আপনি কীভাবে চিনতে পারবেন যে আচরণের সমস্তই একরকম? এবং যে উদ্দেশ্য ছিল? এবং যদি আপনার আচরণটি পরিবর্তন করতে হয় (উদাহরণস্বরূপ বাগ ফিক্স)? এটি খুব সহজেই একটি মিস করা।


3
প্রকৃতপক্ষে, আমার সহকর্মী তার নিজস্ব ব্যতিক্রম ক্লাসটি ডিজাইন করেছেন যা থেকে প্রাপ্ত হয় নাstd::exception এবং আমাদের কোডবেসের মধ্যে এটির প্রয়োগের জন্য প্রতিদিন চেষ্টা করে। আমার অনুমান যে তিনি কোড লিখেছেন এবং বাহ্যিক গ্রন্থাগার তিনি নিজে লিখেছেন না সে জন্য আমাকে শাস্তি দেওয়ার চেষ্টা করেছিলেন।
11'11 এ 9

17
@ereOn আমার কাছে শুনে মনে হচ্ছে আপনার সহকর্মীর প্রশিক্ষণের খুব প্রয়োজন। যাই হোক না কেন, আমি সম্ভবত তার লিখিত গ্রন্থাগারগুলি ব্যবহার করা এড়িয়ে যাব।

2
টেমপ্লেটগুলি এবং কী ব্যতিক্রমগুলি নিক্ষেপ করা হবে তা জেনে চিনাবাদাম মাখন এবং মৃত গেকোগুলির মতো একসাথে চলে। std::vector<>এত সহজ কিছু যে কোনও কারণেই কোনও প্রকারের ব্যতিক্রম ছুঁড়ে ফেলতে পারে।
ডেভিড থর্নলি

3
দয়া করে আমাদের বলুন, আপনি কীভাবে জানেন যে আগামীকাল বাগ বাগের মাধ্যমে কল গাছের নীচে কী ব্যতিক্রম ছুঁড়ে ফেলা হবে?
mattnz

11

আমি মনে করি আপনার সহকর্মী কিছু ভাল পরামর্শ মিশ্রিত করেছেন - আপনি catchযখন কেবল পুনরায় নিক্ষেপ করবেন না তখন আপনাকে কেবল একটি ব্লকে জানা ব্যতিক্রমগুলি পরিচালনা করতে হবে।

এর অর্থ:

try
{
  // Stuff
}
catch (...)
{
  // General stuff
}

খারাপ কারণ এটি চুপচাপ কোনও ত্রুটি আড়াল করবে ।

যাহোক:

try
{
  // Stuff
}
catch (exception_type_we_can_handle&)
{
  // Deal with the known exception
}

ঠিক আছে - আমরা জানি আমরা কী নিয়ে কাজ করছি এবং কলিং কোডে এটি প্রকাশ করার দরকার নেই।

অনুরূপভাবে:

try
{
  // Stuff
}
catch (...)
{
  // Rollback transactions, log errors, etc
  throw;
}

ঠিক আছে, সর্বোত্তম অনুশীলন এমনকি, সাধারণ ত্রুটিগুলি মোকাবেলা করার কোডটি সেই কারণের কোডের সাথে হওয়া উচিত। লেনদেনের পিছনে ঘোরানো বা যা-ই প্রয়োজন, তা জানতে ক্যলের উপর নির্ভর করার চেয়ে এটি আরও ভাল।


9

হ্যাঁ বা না- এর কোনও উত্তরই কেন এমন তা এর যৌক্তিক যুক্তিযুক্ত হওয়া উচিত।

এটা ভুল বলেছি যে কেবল কারণেই আমাকে সেভাবে শেখানো হয়েছে কেবল অন্ধ ধর্মান্ধতা।

একই //Some cleanup; throwউদাহরণ কয়েকবার লিখুন যেমন আপনার উদাহরণ হিসাবে ভুল কারণ কোড নকল এবং এটি একটি রক্ষণাবেক্ষণের বোঝা। এটি একবার লিখে ভাল হয় ভাল।

catch(...)সমস্ত ব্যতিক্রমকে চুপ করে রাখার জন্য একটি লেখা ভুল কারণ আপনার কেবলমাত্র ব্যতিক্রমগুলি পরিচালনা করা উচিত যা আপনি কীভাবে পরিচালনা করতে জানেন এবং সেই ওয়াইল্ডকার্ডের সাহায্যে আপনি আপনার প্রত্যাশার চেয়ে আরও বেশি পরিমাণে ক্যাথ করতে পারেন এবং এটি করার ফলে গুরুত্বপূর্ণ ত্রুটিগুলি নিরব করা যায়।

তবে আপনি যদি একটি এর পরে পুনর্বিবেচনা করেন catch(...), তবে পরবর্তী যুক্তি আর কার্যকর হয় না, কারণ আপনি প্রকৃতপক্ষে ব্যতিক্রমটি পরিচালনা করছেন না, সুতরাং এটি নিরুৎসাহিত করার কোনও কারণ নেই।

আসলে আমি কোনও সমস্যা ছাড়াই সংবেদনশীল ফাংশনে লগ ইন করার জন্য এটি করেছি:

void DoSomethingImportant()
{
    try
    {
        Log("Going to do something important");
        DoIt();
    }
    catch (std::exception &e)
    {
        Log("Error doing something important: %s", e.what());
        throw;
    }
    catch (...)
    {
        Log("Unexpected error doing something important");
        throw;
    }
    Log("Success doing something important");
}

2
আসুন আশা Log(...)নিক্ষেপ করা যাবে না।
ডিডিপ্লিকেটর

2

আমি সাধারণত এখানে পোস্টগুলির মেজাজের সাথে একমত হই, নির্দিষ্ট ব্যতিক্রমগুলি ধরার ধরণটি আমি সত্যিই অপছন্দ করি - আমার মনে হয় যে এর বাক্য গঠনটি এখনও শৈশবকালেই রয়েছে এবং অপ্রয়োজনীয় কোডটি এখনও মোকাবেলা করতে সক্ষম হয় না।

তবে যেহেতু সবাই এই কথাটি বলছে, আমি এই সত্যটি পাইপ করব যে আমি এগুলি অল্প পরিমাণে ব্যবহার করলেও আমি প্রায়শই আমার "ক্যাচ (এক্সপেশন ই)" বিবৃতিটির দিকে তাকিয়ে বলেছি "ড্যাম, আমি চাই যে আমি ফোন করেছি সেই সময়টির নির্দিষ্ট ব্যতিক্রমগুলি বাদ দিন "কারণ আপনি যখন পরে আসবেন তখন উদ্দেশ্যটি কী ছিল এবং ক্লায়েন্ট কী এক নজরে নিক্ষেপ করতে পারে তা প্রায়শই জেনে রাখা ভাল।

আমি "সর্বদা এক্স" এর দৃষ্টিভঙ্গিকে ন্যায়সঙ্গত করছি না, কেবল এটুকু বলেছি যে মাঝে মাঝে তাদের তালিকাভুক্ত দেখতে আসলেই খুব ভাল লাগে এবং আমি নিশ্চিত যে কেউ কেউ মনে করেন যে এটি "সঠিক" পথটি যেতে হবে।

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.