Sunday, February 26, 2017

কোডিং কনভেনশন (coding convention)

আমরা যে কোডগুলো লিখি সেগুলো সাধারণত হাইলেভেল(high-level) প্রোগ্রামিং ভাষায় (যেমন- জাভা)। এর প্রধাণ কারণ, হাইলেভেল প্রোগ্রামিং ভাষাগুলো মানুষের ভাষার কাছাকাছি। এতে করে আমাদের বোঝার সুবিধা হয়। একজন আরেকজনের সহজে কোড পড়তে ও বুঝতে পারে। এইকোডগুলো এজন্যই এভাবে লেখা হয়। কম্পিউটার কিন্তু আমাদের এই হাইলেভেল কোডগুলো বুঝতে পারেনা, এজন্য কম্পাইলারের দরকার হয়। আমাদের কোডগুলো কম্পাইল করার পর মেশিন যাতে বুঝতে পারে এমন কোডে রূপান্তরিত করা হয়। 

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

আমরা যদি কতগুলো নিয়ম মেনে কোডগুলো লিখি, তাহলে এই কোড পড়ে বোঝার প্রক্রিয়টি সহজ হয়ে যায়। এই নিয়মগুলোকে কোডিং কনভেনশন বলা হয়। ভালো প্রোগ্রামার বা ডেভেলপাররা এই নিয়মগুলো কঠিনভাবে করে মেনে চলে। উল্টোভাবেও বলা হয়, একজন ভালো প্রোগ্রামার বা ডেভেলপারকে চেনার উপায় হচ্ছে তার কোড। তার কোড দেখে যদি সহজেই পড়ে বোঝা যায়, তাহলে নিশ্চিৎভাবে তাকে ভালো প্রোগ্রামার বা ডেভেলপার বলা যেতে পারে।  

জাভা প্রোগ্রামিংয়ের জন্য এরকম বেশকিছু নিয়ম বা কনভেনশন রয়েছে। নিচে জাভা কনভেনশনের কতগুলো লিংক দেওয়া হলো- 


Wednesday, February 22, 2017

প্রোগ্রামিং আড্ডা: জাভা প্রোগ্রামিং ও অ্যান্ড্রয়েড: দশটি প্রশ্নের উত্তর

দ্বিমিক কম্পিউটিং আয়োজিত ভাষা দিবসে মাতৃভাষায় প্রোগ্রামিং শেখা নিয়ে একটি বিশেষ আড্ডায় অনেক প্রশ্ন এসেছে। তবে সময় স্বল্পতার জন্য অনেকগুলো প্রশ্নের উত্তর দেওয়া সম্ভব হয়নি। নিচে এমন ১০ টি গুরুত্বপূর্ণ প্রশ্নের উত্তর দেওয়া হলো।


আড্ডাটির ইউটিউব ভিডিও লিংকটিও নিচে দেওয়া হলোঃ




প্রশ্নঃ বাংলাদেশে তো জাভাতে কাজ করে এমন সফটওয়্যার ফার্মের সংখ্যা কম, সুতরাং জাভা শিখে কী লাভ আছে ?
উত্তরঃ বাংলাদেশে মোটেও জাভাতে কাজ করে এমন সফটওয়্যার ফার্মের সংখ্যা কম নয়। জাগবিডিতে একটা সার্ভে করা হয়েছিল তাতে যে সংখ্যা পাওয়া যায়, তার সংখ্যা মোটেও কম নয়। তাছাড়া সামগ্রিকভাবে বাংলাদেশের সফটওয়ার ইন্ডাস্ট্রি এতো বড় নয়। সার্ভেটির লিংক এখানে পাওয়া যাবে- https://goo.gl/O9mJf5


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

প্রশ্নঃ অ্যান্ড্রয়েড অ্যাপ্লিকেশন তৈরির জন্য কী কী মৌলিক ধারণা জানা লাগবে?
উত্তরঃ অ্যান্ড্রয়েড যেহেতু জাভা প্রোগ্রামিং ল্যাংগুয়েজ ব্যবহার করে, সুরতাং জাভার স্ট্যান্ডার্ড এডিশনের আদ্যোপান্ত জানতে হবে। জাভা প্রোগ্রামিং ল্যাংগুয়েজের সিনট্যাক্স থেকে শুরু করে অবজেক্ট ওরিয়েন্টেড কনসেপ্ট, জেনেরিক্স, এক্সেপশন হ্যান্ডেলিং, আইও, কালেকশন ফ্রেমওয়ার্ক ইত্যাদি। অ্যান্ড্রয়েড অ্যাপ্লিকেশন বিল্ড করার জন্য একটি বিল্ডটুল ব্যবহার করে থাকে। এর নাম গ্রাডল। সুতরাং বিল্ডটুল কীভাবে কাজ করে তাও জানতে হবে। এছাড়াও সাধারণত সবধরণের অ্যান্ড্রয়েড অ্যাপ্লিকেশন মূলত ক্লায়েন্ট অ্যাপ হয়ে থাকে, মূল প্রসেসিং রিমুট সার্ভারে হয়ে থাকে। তাই রিমুট সার্ভারের সাথে কীভাবে যোগাযেগা করতে হয় তা জানতে হবে। এক্ষেত্রে অনেকগুলো হেইচটিটিপি(HTTP) ক্লায়েন্ট ব্যবহার করা শিখতে হবে। যদি সার্ভারের অংশটুকুতেও কাজ করতে হয় তাহলে কীভাবে সার্ভারের জন্য ব্যাকএন্ড (back-end) প্রোগ্রামিং করতে সেগুলোও জানতে হবে।


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


প্রশ্নঃ সি না শিখে কী জাভা শেখা যায়।
উত্তরঃ সংক্ষিপ্ত উত্তর, হ্যা। তবে সি প্রোগ্রামিং আপানাকে প্রোগ্রামিংয়ের ধারণা তৈরি করতে সাহায্য করে। এ নিয়ে ধারণা পেতে হলে যেতে পারেন এই লিংকে: http://cpbook.subeen.com/


প্রশ্নঃ অ্যান্ড্রয়েড প্রোগ্রামিংয়ের জন্য জাভার কোন ভার্সনটি মাথায় রাখা উচিৎ?
উত্তরঃ অ্যান্ড্রয়েড জাভা ৭ এর সবগুলো ফিচার সাপোর্ট করে। জাভা ৮ এর সবগুলো না হলেও একটা বড় অংশ সাপোর্ট করে। জাভা ৮ এর নতুন ফিচারগুলো সাপোর্ট করার জন্য অ্যান্ড্রয়েড একটি নতুন কম্পাইলার ব্যবহার করে নাম Jack. বিস্তারিত পাওয়া যাবে এই লিংকে: https://developer.android.com/guide/platform/j8-jack.html


প্রশ্নঃ জাভার এন্টারপ্রাইজ এডিশন কী?
সাধারণত অনেক বড় ধরণের ব্যবসা প্রতিষ্ঠানে ব্যবহৃত অ্যাপ্লিকেশনগুলোতে এন্টাপ্রাইজ শব্দটি ব্যবহার করা হয়। বর্তমানে করপোরেট ইনভাইরনমেন্টে এন্টারপ্রাইজ অ্যাপ্লিকেশন বলতে খুব জটিল, ডিস্ট্রিবিউটেড, কম্পোনেন্ট বেইজড এবং মিশন ক্রিটক্যাল (mission-critical) অ্যাপ্লিকেশন বোঝায়। মিশন ক্রিটিক্যাল অ্যাপ্লিকেশন হলো সেগুলো, যেগুলো কোনো একটি বিশেষ ব্যবসায়িক উদ্দেশ্যে অ্যাপ্লিকেশনটি ব্যবহার করা হয়, যার উপর সম্পূর্ণ ব্যবসাটি নির্ভর করছে। কোন কারণে অ্যাপ্লিকেশনটি কাজ না করলে ব্যবসাটি ক্ষতিগ্রস্থ হয়। এগুলো বিভিন্ন ধরণের প্লাটফর্মের জন্য তৈরি করা হয়, এবং করপোরেট নেটওয়ার্কস, রেসট্রিকটেড নেটওয়ার্কস, ইন্টারনেটের মাধ্যমে ব্যবহার করা হয়, এগুলো খুব ইউজার ফ্রেন্ডলি, ডেটাসেন্ট্রিক, সিকিউরড, এডমিনিস্ট্রটিভ হয় এবং সহজে ম্যানিপুলেট করা যায়। মোটকথা এন্টাপ্রাইজ অ্যাপ্লিকেশন হলো খুব কমপ্লেক্স অ্যাপ্লিকেশন। যেমন- ডাটা স্টোরেজ করা এবং ইউজার রেসট্রিকটেড করা, কাস্টোমার ইনভয়েস, ফ্লাইট বুকিং করা, ব্যাংকিং সিস্টেম অটোমেশন, হেল্থ কেয়ার সিস্টেম এগুলো এন্টারপ্রাইজ অ্যাপ্লিকেশনের উদাহরণ। এগুলোর মাল্টিপল ইন্টারফেজ থাকে পারে, রিমুট কমিউনিকেশন করতে পারে, উন্নত ধরণের গ্রাফিক্যাল ইউজার ইন্টারফেজ থাকে। এটি জাভা স্ট্যান্ডার্ড এডিশনের উপর ভিত্তি করে তৈরি ওয়েব এবং অনেক বড় মাপের এন্টারপ্রাইজ অ্যাপ্লিকেশন তৈরি করার জন্য যে সব কম্পোনেন্ট দরকার হয় তার একটি বিশাল প্যাকেজ। এগুলোকে আলাদা করে নাম দেওয়া হয়েছে জাভা এন্টারপ্রাইজ এডিশন (JEE)। উদাহরণস্বরূপ এর কম্পোনেন্টগুলো হলো-
  • Servlets
  • Java Server Pages (JSP)
  • Java Server Faces (JSF)
  • Enterprise Java Beans (EJB)
  • Java Transaction API (JTA)
  • Java Persistence API (JPA)
  • RESTful Web Services (JAX-RS)
  • Bean Validation
  • Unified Expression Language (EL)
  • Context and Dependency Injection (CDI)
  • Java Message Service message queue API's (JMS)
  • Java WebSocket
  • JSON Processing API (JSON-P)
  • etc.

কিছু এন্টারপ্রাইজ অ্যাপ্লিকেশনের উদাহরণ হলো -

  • কাস্টোমার রিলেশনশিপ ম্যানেজমেন্ট
  • এন্টাপ্রোইজ রিসোর্স প্ল্যানিং
  •  কর্পোরেট আইডেন্টি ম্যানেজমেন্ট
  • কল সেন্টার ও কাস্টোমার সাপোর্ট অ্যাপ্লিকেশন
  • হেল্থ ইনফরমেশন সিস্টেম
  • অটোম্যাটেড বিলিং সিস্টেম
  • ফিনান্সিয়াল, অ্যাকাউন্টিং অ্যাপ্লিকেশন
  • এন্টাপ্রোইজ কন্টেন্ট ম্যানেজমেন্ট
  • বিসনেস প্রসেস ম্যানেজমেন্ট
  • বিসনেস ইন্টেলিজেন্স সফটওয়্যার
  • হিউমেন রিসোর্স ম্যানেজমেন্ট
  • ডকুমেন্ট ম্যানেজমেন্ট সিস্টেম
  • ইন্টারনেট পোর্টাল
ইত্যাদি।
জাভা এন্টারপ্রাইজ এডিশন নিয়ে দ্বিমিকের এই কোর্সটি দেখা যেতে পারে। লিংক: http://dimikcomputing.com/course/javaee-online-course/

প্রশ্নঃ জাভা প্রোগ্রামিং বইয়ে কী কী আছে ?
উত্তরঃ একজন নতুন শিক্ষার্থীর জাভা প্রোগ্রামিং ভাষার যে যে বিষয়গুলোর দিকে নজর দেওয়া উচিৎ সে বিষয়গুলোই এই বইয়ে আলোকপাত করার চেষ্টা করা হয়েছে। বইটি মূলত যারা ইতিমধ্যে একটি প্রোগ্রামিং ভাষা যেমন সি প্রোগ্রামিং ভাষার কিছুটা ধারণা আছে এবং নতুন একটি প্রোগ্রামিং ভাষা বিশেষ করে অবজেক্ট ওরিয়েন্টেড প্রোগ্রামিং ভাষা শিখতে চায় তাদের উদ্দেশ্য করে লেখা হয়েছে। এতে অনেকগুলো বিষয় খুবই গুরুত্বপূর্ণ হওয়া সত্যেও বাদ দেওয়া হয়ছে। যেমন - থ্রেড (Thread), জাভা মেমোরি মডেল (Java Memory Model), অ্যানোটেশন প্রসেসিং (Annotation Processing), ল্যামডা এক্সপ্রেশন (Lambda Expression), নেটওয়ার্কিং (Networking) ইত্যাদি। তবে এগুলোর সবগুলো এডভান্স জাভা প্রোগ্রামিংয়ের জন্য প্রয়োজন হয়। পরবর্তী খণ্ডে যুক্ত করার ইচ্ছা পোষণ করছি।
বইটি সম্পর্কে আরো বিস্তারিত পাওয়া যাবে এই লিংকে: https://goo.gl/FpfSvO 

প্রশ্নঃ ওয়েব প্রোগ্রামিংয়ের ক্ষেত্রে জাভার গুরুত্ব কতটুকু?
উত্তরঃ বর্তমানে সব সফ্টওয়্যারগুলোই মূলত ওয়েব বেইজড হয়ে থাকে। ওয়েব বেইজ অ্যাপ্লিকেশন গুলোর দুটো অংশ থাকে। এক- ব্রাউাজারে রিপ্রেজেন্টেশন যাকে ক্লায়েন্ট সাইড বলা হয়। দুই- ব্যাকএন্ড প্রোগ্রামিং। ক্লায়েন্ট প্রোগ্রামিংয়ের জন্য জাভাস্ক্রিপ্ট ছাড়া আর কোনো উপায় এখনো বের হয়নি। সুতরাং আপনি যদি ওয়েব প্রোগ্রামিং ক্ষেত্রে ক্লায়েন্ট সাইডে কাজ করতে চান, তাহলে জাভাস্ক্রিপ্টের প্রতি গুরুত্ব দিতে হবে। জাভা মূলত ব্যবহার হয় ব্যাকএন্ড প্রোগ্রামিংয়ের ক্ষেত্রে। উপরের একটি প্রশ্নের উত্তরে জাভার ব্যবহার উল্লেখ রয়েছে। এছাড়া জাভা কেনো শেখা উচিৎ বা কোথায় কোথায় ব্যবহার হয় তার জন্যে আগের একটি পোস্ট দেখে নিতে পারেন। লিংক: http://www.bazlur.com/2017/01/why-should-we-learn-java.html


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

Monday, February 20, 2017

নাল (null in Java)

জাভাতে নাল (null) একটি সংরক্ষিত কিওয়ার্ড। আমরা জানি যে, যেকোনো অবজেক্টের একটি রেফারেন্স থাকে। একটি ক্লাস থেকে প্রথমে একটি অবজেক্ট তৈরি করা হয়। সেই অবজেক্টকে আমরা রেফারেন্স দিয়ে অ্যাকসেস করতে পারি। যেমন,

Person person1 = new Person("Bazlur", "Rahman");

এখানে new অপারেটর দিয়ে একটি Person অবজেক্ট তৈরি করা হয়েছে। person1 হচ্ছে সেই অবজেক্টের রেফারেন্স।

Person person2;

এখানে person2 একটি রেফারেন্স। কিন্তু এটি কোনো অবজেক্টকে রেফার করে না। কারণ person2 এর জন্য কোনো অবজেক্ট তৈরি করা হয় নি। এই রকম কোনো রেফারেন্স যদি কোনো অবজেক্টকে রেফারেন্স না করে, তাহলে আমরা বলি এটি একটি নাল রেফারেন্স (Null Reference)। এই রেফারন্সটি কাউকে রেফার করে না।

উপরের person2 একটি নাল (null) বা নাল রেফারেন্স (Null Reference)। এই রেফারেন্স দিয়ে কোনো কাজ করার উপায় নেই। কারণ এর মধ্যে আসলে কিছু নেই। যদি এই রেফারেন্স দিয়ে আমরা কোনো কাজ করতে চাই, তাহলে জাভা ভার্চুয়াল মেশিন NullPointerException থ্রো করবে।

if (person2 != null) {
      System.out.println(person2.getFullName());
}

এই এক্সেপশন থেকে বাঁচতে হলে একটি if স্টেটমেন্ট ব্যবহার করে যাচাই করা যেতে পারে যে, রেফারেন্সটি null কিনা।

জাভা দিয়ে ওয়েব ক্রলার (Java Web Crawler Implementation)

ওয়েব ক্রলার মূলত একটি প্রোগ্রাম যা বিভিন্ন ওয়েব সাইট ব্রাউজ করে বিভিন্ন তথ্য বের করে। একে অনেক সময় স্পাইডার বা ইন্টারনেট বট ও বলা হয়। একটি ওয়েব ক্রলার তৈরি করা একটি ফান প্রজেক্ট হতে পারে।

জাভা দিয়ে এটি তৈরি করার সময় বেশ কতগুলো বিষয় অর্থাৎ ডিজাইন নিয়ে চিন্তা করা যায়। যেমন -
১. এটি সিঙ্গেল থ্রেডেড (Single threaded,) ও সিনক্রোনাস (synchronous) হতে পারে।
২. মাল্টি থ্রেডেড (multi threaded ) ও কনকারেন্ট (concurrent) হতে পারে।
৩. জাভা ইনপুট/আউটপুটের(I/O) জন্যে স্ট্রিম বেইজড বা নিউআইও(NIO) এর বাফার ও চ্যানেল বেইজড হতে পারে।

শুধুমাত্র ফান প্রজেক্ট হিসেবে করতে চাইলে প্রত্যেকটি কম্বিনেশনের জন্যে আলাদা আলাদা করে তৈরি করা যেতে পারে।

সিঙ্গেল থ্রেডেড ও সিনক্রোনাস ক্রলারের তৈরি করা সহজ। এটি তৈরি করতে হলে নিচের কাজগুলো করতে হবে -
১. প্রথমে একটি ওয়েব অ্যাড্রেস থেকে HTML পেইজ ডাউনলোড করতে হবে।
২. HTML পেইজকে পার্স(parse) করতে হবে।
৩. পার্স করারপর প্রয়োজনীয় তথ্যগুলো আলাদা করতে হবে।
৪. পেইজে আরও কোনো লিংক থাকলে সেগুলো আলাদা করতে হবে।
৫. সেই লিংক থেকে আবার ১ নং এর মতো পুরো প্রক্রিয়াটি শুরু করতে হবে।

এই রকম একটি উদাহরণ পাওয়া যাবে এই লিংকে : https://goo.gl/0EiQnC

তবে এর চেয়ে ভাল উপায় হতে পারে যদি মাল্টি থ্রেডেড ক্রলার তৈরি করতে পারি, যাতে অনেকগুলো থ্রেড একই সাথে পাশাপাশি কাজ করবে।

এইরকম একটি ক্রলার তৈরির চেষ্টা করেছিলাম বেশ কিছুদিন আগে। গিটহাবের এই লিংকে এর সোর্সকোড পাওয়া যাবে।

এটি রান করতে হলে আপনার মেশিনে যে যে টুলগুলো থাকবে হবে সেগুলো হলো -
১. গিট (Git)
২. গ্রাডল (Gradle)
৩. জাভা ৮

এটি একটি সংক্ষিপ্ত প্রজেক্ট যাতে ৪ টি ক্লাস রয়েছে এবং দুটি ইন্টারফেস রয়েছে।

মূল অংশ শুরু হবে নিচের ক্লাস থেকে -


এতে প্রথমে একটি বেইজ ইউআরএল দিতে হবে যে ওয়েব সাইট থেকে ক্রল শুরু করবে।

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

সোর্সকোডটি পড়ে বোঝার চেষ্টা করুন। কোনো ফিডব্যাক বা উন্নতি করার উপায় থাকলে ক্লোন করে পুল রিকোয়েস্ট পাঠাতে পারেন। 

Sunday, February 19, 2017

স্ট্রিং পুল কী (What is String Pool)

জাভা ভার্চুয়াল মেশিনে মেমোরি মডেল (Memory Model) দুই ভাবে বিভক্ত। এরা হলো হিপ এবং থ্রেড স্ট্যাক। জাভা অ্যাপ্লিকেশনে যত ধরনের অবজেক্ট তৈরি হয়, সেগুলোর সব থাকে হিপে। স্ট্রিং পুল (String Pool) জাভা হিপের একটি বিশেষ এলাকা।

জাভাতে স্ট্রিং একটি বহুল ব্যবহৃত ক্লাস। যেহেতু এটি ইমিউটেবল, তাই স্ট্রিং নিয়ে কাজ করার সময় হিপে অনেক নতুন নতুন স্ট্রিং অবজেক্ট তৈরি হয়। এছাড়াও স্ট্রিং অবজেক্ট নিজেও অনেক বেশি মেমোরি নিয়ে থাকে। একটি স্ট্রিং অবজেক্ট কত বাইট মেমোরি নেয় তা হিসাব করে বের করে ফেলা যায়।

একটি স্ট্রিং অবজেক্টে থাকে একটি ক্যারেক্টার অ্যারে এবং একটি ইন্টিজার হ্যাশ (Hash)। ইন্টিজারের জন্য দরকার হয় 4 বাইট এবং ক্যারেক্টারের জন্য দরকার হয় 2 বাইট। সুতরাং একটি স্ট্রিংয়ে যদি n সংখ্যক ক্যারেক্টার থাকে তাহলে,


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

উদ্ধৃতি চিহ্ন দিয়ে অর্থাৎ স্ট্রিং লিটারেল ব্যবহার করে নতুন একটি স্ট্রিং তৈরি করা সময়, একইরকম স্ট্রিং অবজেক্ট যদি আগে থেকেই স্ট্রিং পুলে থেকে থাকে, তাহলে নতুন করে আর তৈরি না করে আগের অবজেক্টটির রেফারেন্স দেওয়া হয়।

String string1 = "abcd";

String string2 = "abcd";

উপরের দুটি লাইনের জন্য যদিও দুটি অবেজেক্ট থাকার কথা, কিন্তু আসলে জাভা হিপে একটি স্ট্রিং অবজেক্টই থাকবে, দুটি তৈরি হবে না।

তবে new অপারেটর ও কনস্ট্রাক্টর ব্যবহার করে স্ট্রিং তৈরি করলে তা স্ট্রিং পুলে যায় না।

String str = new String("str");

উপরের লাইনটি আসলে দুটি স্ট্রিং তৈরি করে। এটিকে এভাবে লেখা যায়,

String usingLiteral = "str"; // its in the pool

String newString = new String(usingLiteral); // not in the pool

সুতরাং দেখা যাচ্ছে যে এভাবে স্ট্রিং তৈরি করলে সবসময় অতিরিক্তি স্ট্রিং তৈরি হচ্ছে যা মোটেও কাম্য নয়। সুতরাং স্ট্রিং তৈরি করার জন্য সবসময় লিটারেল ব্যবহার করুন।

এখন যদি স্ট্রিং ইমিউটেবল না হয়, তাহলে একটি স্ট্রিং যদি পরিবর্তন করি, তাহলে আসলে অন্যান্য রেফারেন্সগুলোও পরিবর্তন হয়ে যাবে।

এছাড়াও, আমরা জানি যে স্ট্রিংয়ের হ্যাশকোড (Hashcode) খুব বেশি ব্যবহার করা হয়। যেমন হ্যাশম্যাপ (HashMap)। স্ট্রিং ইমিউটেবল হওয়ায় এটা নিশ্চিত যে, সবসময় হ্যাশকোড একই হবে, সুতরাং আমরা প্রতিবার হ্যাশকোড হিসাব না করে নির্দ্বিধায় ক্যাশিং (Caching) করতে পারি।

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

তাছাড়া স্ট্রিং ইমিউটেবল হওয়ায় এটি স্বাভাবিকভাবে থ্রেড সেইফ (Thread safe) এবং স্বাধীনভাবে যেকোনো থ্রেড অ্যাকসেস করে পারে। এতে করে আমাদেরকে কষ্ট করে এর থ্রেড সেইফটি নিয়ে চিন্তা করতে হয় না।

ফাংশনাল প্রোগ্রামিং কী (What is functional programming)

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

১৯৯০ সালে জন হাগেস (John Hughes) একটি আর্টিকেল প্রকাশ করেন যার বাংলা করলে এমনটা দাড়ায়- 

ফাংশনাল প্রোগ্রামিংয়ে কোনো অ্যাসইনমেন্ট স্টেটমেন্ট নেই। এর অর্থ হলো কোনো ভ্যারিয়েবলে একটি ভ্যালু অ্যাসাইন করা হলে তা আর পরিবর্তন হতে পারে না। অর্থাৎ ফাংশনাল প্রোগ্রামিংয়ে কোন সাইড ইফেক্ট (side effect) নেই। একটি ফাংশন কল শুধুমাত্র কিছু কম্পিউট করবে, কিন্তু এর অন্য কোনো সাইড ইফেক্ট থাকবে না। এতে করে অনেকগুলো প্রোগ্রামিং বাগ থেকে মুক্তি পাওয়া যায়। যেহেতু ফাংশন কলে কোনো সাইড ইফেক্ট নেই, তাই ফাংশন এক্সিকিউশনের ক্রম (আগে না পরে এক্সিকিউট হবে) অপ্রাসঙ্গিক হয়ে যায়- এবং তাই স্টেটমেন্টের ভ্যালু পরিবর্তন হওয়ার কোনো সম্ভবনা নেই। এতে করে কোনো স্টেটমেন্ট যেকোনো সময় ইভ্যালুয়েট করা যায় এবং প্রোগ্রমারকে প্রোগ্রামের নিয়ন্ত্রণ প্রবাহ(flow of control) (অর্থাৎ কোনটিকে আগে আর কোনটিকে পরে কল করতে হবে) থেকে মুক্তি দেয়। যেহেতু এক্সপ্রেশন যে কোনো সময় ইভ্যালুয়েট করা যায়, ফলস্বরূপ ফাংশনকে সহজে ভ্যালু দিয়ে প্রতিস্থাপন করা এবং ভ্যালুকে ফাংশন দিয়ে প্রতিস্থাপন করা যায় যা প্রোগ্রামে রেফারেন্সিয়াল ট্রান্সপারেন্সি (referential transparency) এনে দেয়। এই স্বাধীনতাটুকু প্রোগ্রামকে গাণিতিকভাবে টেস্ট করা সহজ করে দেয়। 

উপরের সংজ্ঞাতে কয়েকটি পরিভাষা(term) ব্যবহার করা হয়েছে। এগুলো এবার একটু দেখে নেওয়া যাক -

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

এই সাইড ইফেক্ট না থাকার অনেকগুলো অর্থ হয়। কোনো ফাংশন কলের ফলে নিচের কাজগুলো হবে না -
১. কোনো ভ্যারিয়েবল পরিবর্তন হবে না।
২. কনসোল বা স্ক্রিনে কোনো কিছু প্রিন্ট হবে না।
৩. ডাটাবেইজ, নেটওয়ার্ক বা অন্যকোনো ডিভাইসে ডেটা রাইট হবে না।
৪. কোনোরকম এক্সেপশন থ্রু করবে না।
ইত্যাদি

রেফারেন্সিয়াল ট্রান্সপারেন্সি :
কোনো একটি ফাংশনকে রেফরেন্সিয়ালী ট্রান্সপারেন্ট বলা যাবে যখন এটি সবসময় একই রকম ইনপুটের জন্য একই ফলাফল কম্পিউট করবে। 

double random = Math.random(); //Take #1 
double pow = Math.pow(2, 2);//Take #2

উপরের কোড অংশে দুটি মেথড কল করা হয়েছে। প্রথমটিকে যতবার কল করা হবে প্রত্যেকবার আলাদা আলাদা ফলাফল দেবে। অপরদিকে দুই নম্বরটিকে যতবার কল করা হোক না কেনো, প্রতি বার একই ফলাফল রিটার্ন করবে। উপরের মেথড দুটির মধ্যে প্রথমটিকে রেফরেন্সিয়ালী ট্রান্সপারেন্ট বলা যাবে না, তবে পরেরটিকে বলা যাবে।

রেফারেন্সিয়াল ট্রান্সপারেন্ট ফাংশনের আরও বেশ কয়েকটি বেশিষ্ট্য হলো -

১. ফাংশনগুলো সবসময় স্বয়ংসম্পূর্ণ। এগুলো কোনো বিশেষ অবস্থার উপর নির্ভর করে না। এগুলোকে যেকোনো অবস্থান থেকে কল করা যাবে। এদেরকে কল করা জন্যে সঠিক আর্গুমেন্টই যথেষ্ট্য।
২. এগুলো একইরকম আর্গুমেন্টের জন্য সবসময় একইরকম ফলাফল প্রকাশ করবে। হঠাৎকরে আশ্চর্য হওয়ার কোনো সম্ভবনা নেই।
৩. এগুলো কখনো এক্সেপশন থ্রো করবে না। এগুলো এরর যেমন – OutOfMemoryError, StackOverflowError
ইত্যাদি দিতে পারে কিন্তু এক্সেপশন নয়। মেমোরির অভাবে প্রোগ্রাম ক্র্যাশ করতেই পারে, তবে এটি একটি রেফারন্সিয়াল ট্রান্সপারেন্ট ফাংশনের জন্য হয় না। এটি অন্যরকম সসম্যা।
৪. এই ফাংশনগুলো কোনোভাবেই এমন কোন পরিস্থিতি তৈরি করবে না যাতে করে অন্য কোনোকিছুর পরিবর্তন না সমস্যা তৈরি হয়। একটি ফাংশন কলের জন্যে কোডের অন্য অংশ ভেঙে যাবে না।
৫. এই ফাংশনগুলো বাইরের কোনো কিছুর অভাবে( যেমন- ফাইল অ্যাকেস, ইন্টারনেট কানেকশন, ডেটাবেইজ কানেকশন ইত্যাদি) বন্ধ হয়ে যাবে না। 

ফাংশনাল প্রোগ্রামিংয়ে এই দুটি বৈশিষ্ট্য ছাড়াও আরও বেশ কতগুলো বৈশিষ্ট্য রয়েছে সেগুলো হলো -

১. প্রথম শ্রেণির (First class) ফাংশন 
২. নামবিহীন (Annonymous) ফাংশন
৩. ক্লোজারস (Closures) 
৪. কারিং (currying)
৫. প্যারামেট্রিক পলিমরফিজম (parametric polymorphism)
৬. বীজগাণিতিক (algebraic) ডাটা টাইপ 
৭. লেজি এভালুয়েশন (Lazy evaluation)

এগুলো নিয়ে পরবর্তীতে আরো বিশদভাবে আলোচনা করা হবে। 

এবার ফাংশনাল প্রোগ্রামিংয়ের কতগুলো সুবিধা নিয়ে আলোচনা করা যাক -

১. যেহেতু একটি ফাংশন একইরকম আর্গুমেন্টের জন্যে একই ফলাফল দেয়, তাই টেস্ট করা সহজ হয়ে যায়। এতে ব্যপকভাবে টেস্ট করে অদ্ভুত সমস্য খুঁজে বের করতে হয় না। 
২. টেস্ট করা সহজ। যেহেতু কোনো সাইড ইফেক্ট নেই, তাই আলাদাকরে মক(Mock) করতে হয় না। যেকোনো ফাংশন এমনিতেই পৃথক। 
৩. সহজে মডুউলার প্রোগ্রাম লেখা যায় কারণ এগুলো শুধু ইনপুট এবং আউটপুট থেকে তৈরি। সাইড ইফেক্ট না থাকার কারণে কোনো ফাংশন কলের ফলে অন্য কোথাও কোনো সমস্যা হতে পারে কিনা তা নিয়ে চিন্তা করতে হয় না, এক্সেপশন থ্রো না করায় ক্যাচ করার প্রশ্ন আসে না, শেয়ার্ড ডেটা না থাকায় থ্রেড সেইফটি নিয়ে চিন্তা করতে হয় না। 
৪. একটি ফাংশনাল প্রোগ্রাম লেখার জন্যে কতগুলো বেইজ ফাংশন থেকে শুরু করতে হয়। সেগুলো কম্মবাইন করে আরও হায়ার লেভেল ফাংশন লিখতে হয়, এভাবে প্রক্রিয়াটি পুনঃব্যবহারের মাধ্যমে একটি ফাংশনে নিয়ে আসতে হয় যা দিয়ে পুরো প্রোগ্রামের কাজটি করা যায়। যেহেতু ফাংশনগুলো রেফারেন্সিয়ালি ট্রান্সপারেন্ট, তাই ফাংশনগুলো কোনো পরিবর্তন না করে অন্য জায়গায় ব্যবহার করা যায়।





Wednesday, February 15, 2017

অ্যবস্ট্রাক্ট ক্লাসের প্রয়োজনীয়তা (why we need abstract class )

পিনাকী ভট্টাচার্যের একটা লেখায় নিচের লাইনগুলো ছিল-

যেমন ফুল যে একটা বিমুর্ত বা এবস্ট্র্যাক্ট ধারণা আমরা অনেকেই হয়ত খেয়াল করিনি। খেয়াল হবে – যদি কাউকে বলি, আমাকে একটা ফুল এনে দেন দেখি। নিশ্চয় সে আনবে জুই, জবা, গন্ধরাজ, দোপাটি, চাঁপা, বোগেনবোলিয়া অথবা রজনীগন্ধা বা আরও কোন দামী কিছু। আমি এক এক করে সব ফিরিয়ে দিব আর বলতে থাকব, ওটা তো জুই, ওটা তো জবা,……..ওটা তো রজনীগন্ধা। আমি শুধু ফুল চাই, কেবল ফুল – যেটা জুইও নয়, জবাও নয়,…… রজনীগন্ধাও নয় – কেবল ফুল চাই আমি।

আমি জানি কেউ আমাকে ফুল এনে দিতে পারবে না, পারে না। কারণ, বাস্তবে really ফুল বলে কিছু নাই; আছে কেবল জুই, জবা, গন্ধরাজ, দোপাটি, চাঁপা, বোগেনবোলিয়া অথবা রজনীগন্ধা বা আরও সব নাম না জানা। কিন্তু তবু ফুল আছে; আছে বিমুর্ততায়, আমাদের ভাবের মধ্যে। “ফুল’ ধরনাটাই একটা এবস্ট্র্যাকশন।

আমি কেনো এই উদ্ধৃতি দিলাম তা এবার বলি,

অবজেক্ট ওরিয়েন্টেড কনসেপ্ট পড়তে গিয়ে অনেকেই ভাবে, অ্যাবস্ট্রাক্ট ক্লাসের প্রয়োজনীয়তা কী? উপরের ব্যাখ্যায় বোঝা গেলো, ফুল একটি ধারণা মাত্র, এটি কোনো কনক্রিট কিছু না। তবে এর কনক্রিট উদাহরণ হতে পারে জুই, জবা, গন্ধরাজ ইত্যাদি।

অবজেক্ট ওরিয়েন্টেড কনসেপ্টে এই ফুল ধারণাটির জন্যে অ্যবস্ট্রাক্ট ক্লাস ব্যবহার করা যেতে পারে। উদাহরণ -



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

Monday, February 13, 2017

এনাম (Enum)

জাভাতে এনাম (enum) একটি বিশেষ টাইপ। একটি নির্দিষ্ট সংখ্যক কনস্ট্যান্ট (Constant) তৈরি করতে এটি ব্যবহার করা হয়। যেমন, সপ্তাহের দিনের নাম (days of the week), বছরে মাসের নাম (month in the year), দিক (উত্তর, দক্ষিণ, পূর্ব, পশ্চিম) ইত্যাদি।
উদাহরণ,

public enum Day {
   SATURDAY,
   SUNDAY,
   MONDAY,
   TUESDAY,
   WEDNESDAY,
   THURSDAY,
   FRIDAY
}

উদাহরণটি Day নামে একটি এনাম তৈরি করা হয়ছে। এতে সাতটি কনস্ট্যান্ট রয়েছে। এনাম তৈরি করতে ক্লাস বা ইন্টারফেসের মতো একটি কিওয়ার্ড enum ব্যবহার করা হয়েছে।
এনাম সরাসরি ডট('.') অপারেটর ব্যবহার করে অ্যাকসেস করা যায় এবং ভ্যারিয়েবল হিসেবে ব্যবহার করা যায়। উদাহরণ,

Day day = Day.SATURDAY;

এনাম, if স্টেটমেন্টে ব্যবহার করা যায়। উদাহরণ,

 public class EnumExample {
   public void displayDay(Day day) {
      if (day == Day.SATURDAY) {
         System.out.println("Its saturday! Weekend!");
      } else if (day == Day.FRIDAY) {
         System.out.println("It's Friday!! Weekend!");
      } else {
         System.out.println("Weekday!");
      }
   }

   public static void main(String[] args) {
      EnumExample enumExample = new EnumExample();
      Day day = Day.SATURDAY;
      enumExample.displayDay(day);
   }
}

এনাম সুইচ স্টেটমেন্টে ব্যবহার করা যায়। উদাহরণ,

public void displayDay(Day day) {
   switch (day) {
      case SATURDAY:
         System.out.println("Its saturday! Weekend!");
         break;
      case FRIDAY:
         System.out.println("It's Friday!! Weekend!");
         break;
      default:
         System.out.println("Weekday!");
         break;
   }
}

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

Day[] values = Day.values();
for (Day day : values) {
   System.out.println(day);
}


আউটপুট,

SATURDAY
SUNDAY
MONDAY
TUESDAY
WEDNESDAY
THURSDAY
FRIDAY

এতে ফিল্ড, মেথড এবং কনস্ট্রাক্টর লেখা যায়। উদাহরণ,


public enum Level {
   HIGH(3),
   MEDIUM(2),
   LOW(1);

   private final int levelCode;

   Level(int levelCode) {
      this.levelCode = levelCode;
   }

   public int getLevelCode() {
      return this.levelCode;
   }
}


এছাড়াও এনাম সম্পর্কে বেশ কতগুলো তথ্য যা জেনে রাখা বিশেষ প্রয়োজন,
1. এনাম ডিক্লেয়ারেশন মূলত একটি ক্লাস যা কিনা java.lang.Enum ক্লাসকে এক্সটেন্ড করে। একে এক্সটেন্ড করা যায় না বা অন্য কোনো ক্লাসকে এটি এক্সটেন্ড করতে পারে না। তবে এনাম ইন্টারফেস ইমপ্লিমেন্ট করতে পারে।
2. এনাম টাইপ সেইফ। অর্থাৎ কোন এনাম ভ্যারিয়েবলে অন্য কোনো ভ্যালু অ্যাসাইন করা সম্ভবন না। উদাহরণ,

Day day = Day.MONDAY;
day = 4;

এখানে দ্বিতীয় লাইনটি বৈধ নয়।
3. এনামকে == অপারেটর ব্যবহার করে এবং equals() মেথড ব্যবহার করে দুই ভাবেই তুলনা করা যায়।
4. এনামকে নিউ (new) অপারেটর ব্যবহার করে এর ইনস্ট্যান্স তৈরি করা যাবে না।

Sunday, February 12, 2017

জাভা প্রোগ্রামিং বই



সূচীপত্র

লেখকের কথা

লেখক পরিচিতি

অধ্যায় শূন্য: উপক্রমণিকা

অধ্যায় এক: প্রথম জাভা প্রোগ্রাম

  • ১.১ – প্রোগ্রামিং ভাষা কী?
  • ১.২ – কেন জাভা?
  • ১.৩ – জাভা কীভাবে কাজ করে?
    • ১.৩.১ – বাইটকোড (Bytecode)
    • ১.৩.২ – জাভা ভার্চুয়াল মেশিন (JVM)
    • ১.৩.৩ – জাস্ট ইন টাইম (JIT) কম্পাইলার
    • ১.৩.৪ – আরও কিছু টার্মিনোলোজি
    • ১.৩.৫ – জাভা প্ল্যাটফর্মের সাবসেট
  • ১.৪ – জাভা ইনস্টল (Install) করা
    • ১.৪.১ – উইন্ডোজে জাভা ইনস্টল করা
    • ১.৪.২ – উইন্ডোজের প্রথম জাভা প্রোগ্রাম
    • ১.৪.৩ – লিনাক্সে জাভা ইনস্টল করা
    • ১.৪.৪ – লিনাক্সে প্রথম জাভা প্রোগ্রাম
  • ১.৫ – আইডিই (IDE) এর ব্যবহার
  • ১.৬ – আরও কয়েকটি সহজ প্রোগ্রাম
    • ১.৬.১ – যোগ, বিয়োগ, গুন, ভাগ করার প্রোগ্রাম
    • ১.৬.২ – ইনপুট নেওয়া
  • ১.৭ – অনুশীলনী

অধ্যায় দুই: সিনট্যাক্স (Syntax)

  • ২.১ – অবজেক্ট (Object) ও ক্লাস (Class)
    • ২.১.১ – অবজেক্ট (Object)
    • ২.১.২ – অবজেক্ট (Object)
  • ২.২ – জাভা প্রোগ্রামের উপাদানসমুহ
  • ২.৩ – জাভা মেথড (Java Method)
  • ২.৪ – অবজেক্ট ইনস্ট্যান্সিয়েশন (Object Instantiation)
  • ২.৫ – মেথড ওভারলোডিং (Method Overloading)
  • ২.৬ – কনস্ট্রাক্টর (Constructor)
  • ২.৭ – মেথডের ব্যবহার
  • ২.৮ – প্রিন্টিং (Printing)
  • ২.৯ – প্যারামিটার (Parameter) ও আর্গুমেন্ট (Argument)
  • ২.১০ – প্যাকেজ নাম (Package Name) ও ডিরেক্টরি স্ট্রাকচার (Directory Structure)
  • ২.১১ – প্যাকেজ ইমপোর্ট (Import) করা
  • ২.১৩ – আরও কিছু নিয়ম
  • ২.১৪ – অনুশীলনী

অধ্যায় তিন: ডেটা টাইপ (Data Type), অপারেটর (Operator) এবং এক্সপ্রেশন (Expression)

  • ৩.১ – ভ্যারিয়েবল (Variable)
  • ৩.২ – ভ্যারিয়েবল প্রিন্ট করা
  • ৩.৩ – ডেটা টাইপ (Data Type)
    • ৩.৩.১ – প্রিমিটিভ টাইপ (Primitive Type)
  • ৩.৪ – র‍্যাপার ক্লাস (Wrapper Class)
  • ৩.৫ – লিটারেল (Literal)
    • ৩.৫.১ – ইন্টিজার লিটারেল (Integer Literal)
    • ৩.৫.২ – ফ্লোটিং পয়েন্ট লিটারেল (Floating Point Literal)
    • ৩.৫.৩ – ক্যারেক্টার (Character) ও স্ট্রিং লিটারেল (String literal)
    • ৩.৫.৪ – স্যাংখিক (Numeric) লিটারেলে আন্ডারস্কোর চিহ্নের ব্যবহার
    • ৩.৫.৫ – এসকেপ সিকোয়েন্স (Escape Sequence)
  • ৩.৬ – অপারেটর (Operator)
    • ৩.৬.১ – অ্যাসাইনমেন্ট অপারেটর (Assignment Operator)
    • ৩.৬.২ – অ্যারিথমেটিক অপারেটর (Arithmetic Operator)
    • ৩.৬.৩ – ইন্টিজার সংখ্যার ভাগ অপারেশন (Integer Division) ও ফ্লোটিং পয়েন্ট সংখ্যার ভাগ অপারেশন (Floating Point division)
    • ৩.৬.৪ – রাউন্ডিং ত্রুটি বা এরর (Rounding Error)
    • ৩.৬.৫ – স্ট্রিং অপারেশন (String Operation)
    • ৩.৬.৬ – ইউনারি (Unary) অপারেটর
    • ৩.৬.৭ – ইকুয়ালিটি (Equality) এবং রিলেশনাল (Relational) অপারেটর
    • ৩.৬.৮ – ওভারফ্লো (Overflow) / আন্ডারফ্লো (Underflow)
    • ৩.৬.৯ – টাইপ কনভার্সন (Type Conversion) / টাইপ কাস্টিং (Type Casting)
  • ৩.৭ – এক্সপ্রেশন (Expression), স্টেটমেন্ট (Statement) এবং ব্লক (Blocks)
    • ৩.৭.১ – এক্সপ্রেশন (Expression)
    • ৩.৭.২ – স্টেটমেন্ট (Statement)
    • ৩.৭.৩ – ব্লক (Block)
    • ৩.৭.৪ – ভ্যারিয়েবল স্কোপ (Scope of a Variable)
  • ৩.৮ – অনুশীলনী

অধ্যায় চার: কন্ট্রোল ফ্লো (Control Flow), লুপিং (Looping) ও ব্রাঞ্চিং (Branching)

  • ৪.১ – ডিসিশন মেকিং স্টেটমেন্ট (Decision Making Statement)
    • ৪.১.১ – If, If-else, if-else-if
    • ৪.১.২ – নেস্টেড (Nested) If-else
    • ৪.১.৩ – সুইচ (Switch)
  • ৪.২ – লুপ (Loop)
    • ৪.২.১ – While লুপ
    • ৪.২.২ – For লুপ
    • ৪.২.৩ – Do-While লুপ
  • ৪.৩ – ব্রেক (break) এবং কন্টিনিউ (continue)
  • ৪.৪ – রিটার্ন (return) স্টেটমেন্ট
  • ৪.৫ – অনুশীলনী

অধ্যায় পাঁচ: অ্যারে (Array)

  • ৫.১ – অ্যারে ডিক্লেয়ারেশন (Array Declaration), ক্রিয়েশন (Creation) এবং অ্যাকসেস (Access)
  • ৫.২ – মাল্টি-ডাইমেনশনাল অ্যারে (Multi-Dimensional Array)
  • ৫.৩ – এনহ্যান্সড (Enhanced) For লুপ বা For-Each লুপ
  • ৫.৪ – অ্যারে কপি করা (Copying)
  • ৫.৫ – অনুশীলনী

অধ্যায় ছয়: অবজেক্ট ওরিয়েন্টেড প্রোগ্রামিং (Object Oriented Programming)

  • ৬.১ – অবজেক্ট (Object) ও ক্লাস (Class)
    • ৬.১.১ – অবজেক্ট (Object)
    • ৬.১.২ – ক্লাস (Class)
  • ৬.২ – অবজেক্ট ওরিয়েন্টেড প্রোগ্রামিং (Object Oriented Programming)
    • ৬.২.১ – অবজেক্ট অরিয়েন্টেডেট প্রোগ্রামিংয়ের প্রয়োজনীয়তা এবং উৎপত্তি
  • ৬.৩ – ইনহেরিটেন্স (Inheritence)
    • ৬.৩.১ – ফাইনাল ক্লাস (Final Class)
    • ৬.৩.২ – মেথড ওভাররাইডিং (Method Overriding)
    • ৬.৩.৩ – অ্যানোটেশন (Annotation) @Override
    • ৬.৩.৪ – super কিওয়ার্ড
    • ৬.৩.৫ – ফাইনাল (Final) মেথড
    • ৬.৩.৬ – অবজেক্ট কম্পোজিশন (Object Composition)
  • ৬.৪ –পলিমরফিজম (Polymorphism)
    • ৬.৪.১ –ভ্যারিয়েবল টাইপ এবং অবজেক্ট টাইপ
    • ৬.৪.২ –আপ-কাস্টিং (Upcasting) এবং ডাউনকাস্টিং (Downcasting)
  • ৬.৫ – অ্যাবস্ট্রাক্ট ক্লাস এবং ইন্টারফেস (Abstract class & interface)
    • ৬.৫.১ – অ্যাবস্ট্রাক্ট ক্লাস (Abstract class)
    • ৬.৫.২ – অ্যাবস্ট্রাক্ট মেথড (Abstract Method)
    • ৬.৫.৩ – অ্যাবস্ট্রাক্ট ক্লাস এবং অ্যাবস্ট্রাক্ট মেথডের কতগুলো নিয়ম
    • ৬.৫.৪ – ইন্টারফেস (Interface)
    • ৬.৫.৫ – ইন্টারফেস বনাম অ্যাবস্ট্রাক্ট
  • ৬.৬ – এনক্যাপসুলেশন (Encapsulation)
    • ৬.৬.১ – ডিফল্ট অ্যাকসেস (Default Access)
    • ৬.৬.২ – প্রাইভেট অ্যাকসেস মডিফায়ার (Private Access Modifier) – private
    • ৬.৬.৩ – পাবলিক অ্যাকসেস মডিফায়ার (Public Access Modifier) – public
    • ৬.৬.৪ – প্রোটেক্টেড অ্যাকসেস মডিফায়ার (Protected Access Modifier) – protected
    • ৬.৬.৫ – অ্যাকসেস লেভেল টেবিল
    • ৬.৬.৬ – এনক্যাপসুলেশন সংক্রান্ত জরুরী কিছু বিষয়
  • ৬.৭ – অনুশীলনী

অধ্যায় সাত: জাভা এক্সেপশন হ্যান্ডেলিং (Java Exception handling)

  • ৭.১ – try ব্লক
  • ৭.২ – catch ব্লক
  • ৭.৩ – finally ব্লক
  • ৭.৪ – জাভা এক্সেপশন হায়ারার্কি (Java Exception Hierarchy)
  • ৭.৫ – চেকড এক্সেপশন (Checked Exception) ও আনচেকড এক্সেপশন (Unchecked Exception)
    • ৭.৫.১ – আনচেকড এক্সেপশন (Unchecked Exception)
    • ৭.৫.২ – চেকড এক্সেপশন (Checked Exception)
    • ৭.৫.৩ – চেকড এক্সেপশন এবং জাভা কম্পাইলার
  • ৭.৬ – এক্সেপশন ডিক্লেয়ারেশন (Exception Declaration) ও থ্রোয়িং (Throwing)
  • ৭.৭ – এক্সেপশন থেকে তথ্য সংগ্রহ করা
  • ৭.৮ – স্ট্যাক-ট্রেস (Stack Trace)
  • ৭.৯ – মেথড কল স্ট্যাক ও এক্সেপশন (Method Call Stack & Exception)
  • ৭.১০ – সাধারণ এক্সেপশন ক্লাস
  • ৭.১১ – ইউজার ডিফাইনড এক্সেপশন (User Defined Exception)
  • ৭.১২ – ফল্ট টলারেন্ট সিস্টেম (Fault Tolerant System) এর জন্য জাভা এক্সেপশন
  • ৭.১৩ – অনুশীলনী

অধ্যায় আট: জেনেরিকস (Generics)

  • ৮.১ – জাভাতে জেনেরিকস
  • ৮.২ – জেনেরিকস (Generics) এবং সাবটাইপিং (Subtyping)
  • ৮.৩ – বাউন্ডেড টাইপ (Bounded Types)
  • ৮.৪ – ওয়াইল্ডকার্ড আর্গুমেন্ট (Wildcard Arguments)
  • ৮.৫ – জেনেরিক মেথড (Generic Method)
  • ৮.৬ – টাইপ ইরেইজার (Type erasure)
  • ৮.৭ – অনুশীলনী

অধ্যায় নয়: জাভা আই/ও (I/O)

  • ৯.১ – ফাইল নিয়ে কাজ
    • ৯.১.১ – পাথ (Path)
    • ৯.১.২ – ফাইল তৈরি
    • ৯.১.৩ – পাথ সেপারেটর (Path separator)
    • ৯.১.৪ – ডিরেক্টরি তৈরি
    • ৯.১.৫ – ফাইল রিনেমিং (File Renaming), ফাইল কপিইং (File Copying) এবং ফাইল ডিলিটিং (File Deleting)
    • ৯.১.৬ – ফাইলের তালিকা বের করা
    • ৯.১.৭ – ফাইল ফিল্টার (File Filter)
  • ৯.২ – ইনপুট/আউটপুট স্ট্রিম (Input/Output Stream)
    • ৯.২.১ – স্ট্রিমের প্রকারভেদ
    • ৯.২.২ – ইনপুট স্ট্রিম (InputStream) তৈরি
    • ৯.২.৩ – ইনপুট স্ট্রিম থেকে ডেটা পড়া
    • ৯.২.৪ – আউটপুট স্ট্রিম (OutputStream) তৈরি
    • ৯.২.৫ – আউটপুট স্ট্রিমে ডেটা রাইট করা
    • ৯.২.৬ – ক্যারেক্টার স্ট্রিম (Character Stream)
    • ৯.২.৭ – রিডার (Reader) ব্যবহার করে ডেটা রিড করা
    • ৯.২.৮ – রাইটার (Writer) ব্যবহার করে ডেটা রাইট করা
    • ৯.২.৯ – System.in, System.out, and System.error
    • ৯.২.১০ – প্রিমিটিভ ডেটা রিড/রাইট করা
  • ৯.৩ – অনুশীলনী

অধ্যায় দশ: জাভা এন আই/ও (NIO)

  • ১০.১ – জাভা এনআইও (NIO) কী?
  • ১০.২ – বাফার (Buffer)
  • ১০.৩ – চ্যানেল (Channel)
  • ১০.৪ – ফাইল রিড করা
  • ১০.৫ – ফাইল রাইট করা
    • ১০.৫.১ – try-with-resource
  • ১০.৬ – একত্রে রিড এবং রাইট করা
  • ১০.৭ – ক্যারেক্টার সেট (Character Set)
  • ১০.৮ – অনুশীলনী

অধ্যায় এগারো: কালেকশন ফ্রেমওয়ার্ক (Collection Framework)

  • ১১.১ – কালেকশন (Collection)
  • ১১.২ – লিস্ট (List)
  • ১১.৩ – স্ট্যাক (Stack)
  • ১১.৪ – ইটারেবল (Iterable) ও ইটারেটর (Iterator)
  • ১১.৫ – সেট (Set)
  • ১১.৬ – কিউ (Queue)
  • ১১.৭ – ম্যাপ (Map)
    • ১১.৭.১ – হ্যাশম্যাপ (HashMap)
    • ১১.৭.২ – ট্রিম্যাপ (TreeMap)
    • ১১.৭.৩ – হ্যাশটেবিল (HashTable)
    • ১১.৭.৪ – লিঙ্কড হ্যাশম্যাপ (LinkedHashMap)
  • ১১.৮ – কালেকশন অর্ডারিং/সর্টিং (Collection Sorting/Ordering)
  • ১১.৯ – সার্চিং (Searching)
  • ১১.১০ – অনুশীলনী

অধ্যায় বারো: স্ট্রিং অপারেশন (String Operations)

  • ১২.১ – স্ট্রিং কনক্যাটিনেশন (Concatenation)
  • ১২.২ – স্টিংয়ের কিছু গুরুত্বপূর্ণ মেথড
  • ১২.৩ – স্ট্রিং পুল (String Pool)
  • ১২.৪ – স্ট্রিং বিল্ডার (StringBuilder) এবং স্ট্রিং বাফার (StringBuffer)
  • ১২.৫ – অনুশীলনী

অধ্যায় তের: জাভা ম্যাথ এপিআই (Math API) ও ইউটিলিটি ক্লাস (Utility Class)

  • ১৩.১ – জাভা ম্যাথ এপিআই
  • ১৩.২ – র‍্যান্ডম নম্বর (Random Numbers)
  • ১৩.৩ – বিগ-ইন্টিজার (BigInteger) ও বিগ-ডেসিমাল (BigDecimal)

অধ্যায় চৌদ্দ: ইউনিট টেস্টিং (Unit Testing)

  • ১৪.১ – JUnit অ্যানোটেশন (Annotation)
  • ১৪.২ – অ্যাসার্ট স্টেটমেন্ট (Assert statements)
  • ১৪.৩ – ফেইলড টেস্ট কেইস (Failed Test Case)

পরিশিষ্ট ১ : এনাম (Enum)

পরিশিষ্ট ২: নাল (null )

পরিশিষ্ট ৩ : Object ক্লাস

পরিশিষ্ট ৪: জাভা কী পাস-বাই-ভ্যালু (Pass-by-Value)?

পরিশিষ্ট ৫ : জাভা স্ট্রিং ফরম্যাটিং

পরিশিষ্ট ৬ : একটি ক্যালকুলেটর

পরিশিষ্ট ৭ : ক্যারেক্টার এনকোডিং (Character Encoding)

পরিশিষ্ট ৮ : ডিবাগিং (Debugging)

পরিশিষ্ট ৯ : জাভা কিওয়ার্ড (Java Keywords)

পরিশিষ্ট ১০ : জাভা কীভাবে কাজ করে এবং কীভাবে ভালো পারফর্ম করে

পরিশিষ্ট ১১ : বাংলাতে জাভা প্রোগ্রামিং



প্রাপ্তিস্থান

  • রকমারি ডট কম
  • হক লাইব্রেরী, নীলক্ষেত, ঢাকা
  • মানিক লাইব্রেরী, নীলক্ষেত, ঢাকা
  • রানা বুক সাপ্লাই, নীলক্ষেত, ঢাকা

Wednesday, February 8, 2017

জাভা কী পাস-বাই-ভ্যালু (Pass-by-Value)

যখন একটি মেথডে আর্গুমেন্ট হিসেবে একটি অবজেক্ট পাঠানো হয় তখন কী ঘটনা ঘটে? এটি কি পাস-বাই-ভ্যালু (Pass-by-Value) না কি পাস-বাই-রেফারেন্স (Pass-by-Reference)?

এই প্রশ্ন দুটির উত্তর দিতে হলে আমাদের জানতে হবে অবজেক্টের রেফারেন্স কী।

জাভাতে অবজেক্টগুলো প্রোগ্রাম মেমোরির হিপ অংশে থাকে। এর একটি ঠিকানা বা অ্যাড্রেস আছে। ভ্যারিয়েবল মূলত সেই অবজেক্টের অ্যাড্রেস ধরে রাখে যাকে আমরা বলি অবজেক্টের রেফারেন্স। আমরা যখন কোনো মেথডে আর্গুমেন্ট হিসেবে একটি ভ্যারিয়েবল বা অবজেক্টের রেফারেন্স পাস করি তখন আসলে সেই অবজেক্টের রেফারেন্সটি পাঠাই না বরং সেই রেফারেন্সের একটি কপি পাঠাই। কোনো একটি অবজেক্টের রেফারেন্স ভ্যালু যদি হয়, 66d3c617 তাহলে মেথড আর্গুমেন্ট হিসেবে এই সংখ্যাটির একটি কপি আর্গুমেন্ট হিসেবে যায়। এর মানে দাঁড়ায় আমরা আসলে রেফারেন্সটি পাঠাচ্ছি না বরং সেই রেফারেন্সের কপি পাঠাচ্ছি।

[code]

public class Person {
   private String name;
   public Person(String name) {
      this.name = name;
   }
   public void setName(String name) {
      this.name = name;
   }
   public static void main(String[] args) {
      Person person; // 1
      person = new Person("Bazlur"); // 2
      changePersonName(person); // 3
   }

   public static void changePersonName(Person copyOfTheReferenceOfPersonObject) {
      copyOfTheReferenceOfPersonObject.setName("Rahman");
   }
}

[/code]

উপরের কোডটি খেয়াল করুন, 
  1. প্রথমে একটি Person ক্লাসের ভ্যারিয়েবল person তৈরি করেছি। 
  2. তারপর এর অবজেক্ট তৈরি করেছি যা কিনা মেমোরির হিপ অংশে রয়েছে। এর একটি রেফারেন্স তৈরি হয়েছে। ধরা যাক এটি, 66d3c617 
  3. person ভ্যারিয়েবলটি Person ক্লাসের একটি অবজেক্টের রেফারেন্স ধরে রাখে যা কিনা changePersonName() মেথডের আর্গুমেন্ট হিসেবে পাস করা হয়েছে। 
এই মেথডটি যখনই কল করা হয়েছে তখন, person ভ্যারিয়েবলের একটি কপি তৈরি হয়েছে যা এই মেথডের লোকাল ভ্যারিয়েবল copyOfTheReferenceOfPersonObject। তার মানে দাঁড়ায়, এখানে person এবং copyOfTheReferenceOfPersonObject এই দুটি ভ্যারিয়েবলের ভ্যালু একই অর্থাৎ 66d3c617। এর অর্থ, এই ভ্যারিয়েবল দুটি একই অবজেক্টকে নির্দেশ বা রেফার করে।

এতে করে আমরা সহজেই বলতে পারি জাভা পাস-বাই-রেফারেন্স-ভ্যালু (Pass-by-Reference-Value) বা পাস-বাই-কপি-অব-দি-ভ্যারিয়েবল-ভ্যালু (Pass-by-Copy-of-the-Variable-Value) অথবা সহজে পাস-বাই-ভ্যালু (Pass-by-Value)।

Monday, February 6, 2017

Types of Learners - the dabblers, the hacker, and the master

জর্জ লেনার্ডের একটা বই আছে, নাম মাস্টারি (MASTERY The Keys to Success and Long-Term Fulfillment)। বইয়ে তিনি তিন ধরণের শিক্ষার্থী(learners) এর কথা বলেছেন - 

The dabblers, the hacker, and the master. 

Dabblers হলো যারা খুব সহজেই একটা বিষয় নিয়ে আবেগকম্পিত(exicited) হয়ে যায়। নতুন কিছু পেলেই খুশিতে আকাশ পাতাল এক করে লাফিয়ে পরে এবং শিখতে শুরু করে এবং সবাইকে বলা শুরু করে। কিন্তু সমস্যা হলো এরা এই আগ্রহ খুব বেশি দিন ধরে রাখতে পারে না। আগ্রহ হারিয়ে যায়। তখন অন্য কিছু নিয়ে লাফাতে শুরু করে। 

এর পরের গোষ্ঠী হলো হ্যাকার। এরা একটা নির্দিষ্ট পরিমাণ পর্যন্ত শিখে। They get to reasonably good at things. এরা এই বিষয় নিয়ে কাজ করে যেতে পারে। যখন learning plateau চলে আসে অর্থাৎ একটা জিনিস শিখতে শরু করতে আস্তে আস্তে ইমপ্রুভ হয়, কিন্তু একটা সময় ইমপ্রুভ হওয়া বন্ধ হয়ে যায়, তখন তারা থামিয়ে দেয় এবং অন্য কিছু তে মনোযোগ দেয়। 

অন্যদিকে মাস্টার হলো যারা কোনো কিছুতে মাস্টারি অর্জন করে ফেলেছে তারা নয়, বরং যারা কোনো একটা বিষয়ে প্রতিজ্ঞাবদ্ধ (he is somebody that's commited to continual improvement)। learning plateau চলে আসলেও থামিয়ে দেওয়া যাবে না। তিনি বলেন, এই সময়ে সবচেয়ে বেশি শেখা যায়। যদিও এটা একটা কঠিন সময় কিন্তু এর পরেই আসলে বড় জাম্প দেওয়া যায়। 

প্রোগ্রামিং বেশ কমপ্লেক্স একটা স্কিল। এখানে dabblers হলে আসলে কোনো লাভ নেই। হ্যাকার হলেও চলে। তবে মাস্টার হতে হলে এই কমিটমেন্টটা থাকতে হবে।

Saturday, February 4, 2017

ক্যারেক্টার সেট (Character Set)

ক্যারেক্টার সেট

ক্যারেক্টার সেট নিয়ে কথা বলার আগে একটু এর পেছনের ইতিহাস জেনে নেওয়া উচিৎ। 


টেলিগ্রাফ

একটা সময়ে আমাদের যোগাযোগের একমাত্র মাধ্যম ছিল টেলিগ্রাফ। এতে করে তারের মাধ্যমে বৈদ্যুতিক সিগন্যাল পাঠানো হতো যা প্রায় ১৫০ বছর ধরে ব্যবহার করা হয়। স্যার চার্লস হুইটস্টোন (Sir Charles Wheatstone) এবং স্যার উইলিয়াম ফদারগ্রিল কুক (Sir William Fothergril Cooke) ১৮৩৭ সালে ইংল্যান্ডে সর্ব প্রথম রেলওয়ে টেলিগ্রাফ প্রবর্তন করেন যা কুক ও হুইটস্টোন টেলিগ্রাফ নামে পরিচিত। এতে কতগুলো চুম্বকশলাকা ব্যবহার করা হতো যেগুলোকে তড়িৎচুম্বকীয় আবেশের মাধ্যমে ঘড়ির কাঁটার দিকে (Clockwise) বা ঘড়ির কাঁটার বিপরীত দিকে (Anti-Clockwise) ঘোরানো যেত। চুম্বকশলাকা কোন দিকে ঘুরবে তা নির্ভর করতো টেলিগ্রাফের তারে বিদ্যুত কোন দিকে প্রবাহ হচ্ছে তার উপর। এতে সিগন্যাল ট্রান্সমিশনের যতগুলো চুম্বকশলাকা থাকত ঠিক ততগুলো তারের প্রয়োজন হতো। চুম্বকশলাকাগুলো একটি ডায়মন্ড আকৃতির গ্রিডের ওপরে বসানো থাকতো। এক বা একাধিক চুম্বকশলাকাকে আবিষ্ট করা হতো, তখন চুম্বকশলাকাগুলো গ্রিডের ভেতর একটি বর্ণ নির্দেশ করতো।

ঠিক একই বছর স্যামুয়েল মোর্স (Samuel Morse) আমেরিকান টেলিগ্রাফ প্রবর্তন করেন যা অনেক ক্ষেত্রেই কোক ও হুটিস্টোন টেলিগ্রাফ থেকে সহজ। এতে সিগনাল ট্রান্সমিশনের জন্য একটি তার ব্যবহার করার প্রয়োজন হতো এবং কোনো টেক্সট ইনফরমেশন কতগুলো অন অফ টোন বা লাইট বা ক্লিকের মাধ্যমে পাঠানো হতো যা একজন দক্ষ ব্যক্তি সহজেই বুঝতে পারতো কোনো রকম আদালা যন্ত্র ছাড়াই। একে মোর্সকোড (Morse Code) বলা হয়।

মোর্স কোড মূলত কতগুলো অন (On)/অফ (Off) এর ধারা এবং এগুলো বিভিন্ন দৈর্ঘ্যের হয়। সাধারণত অন সিগন্যালের দৈর্ঘ্য বড় হয় এবং একে ড্যাশ (-) দিয়ে উপাস্থাপন করা হয়। এর উচ্চারণ ডাহ (dah)। অফ সিগন্যালের দৈর্ঘ্য তুলনামূলক ভাবে একটু ছোট হয় একে ডট (.) দিয়ে উপস্থাপন করা হয় এবং এর উচ্চারণ ডিট (dit)। কতগুলো ডট এবং ড্যাশের সিকোয়েন্স দিয়ে একেকটি বর্ণকে উপস্থাপন করা হতো। একটি বর্ণে কতগুলো ড্যাশ এবং ডট থাকবে তার একটি চার্ট তৈরি করা হয়।


চিত্র : মোর্স কোড এর চার্ট

মোর্স কোড একটি বিশেষ আবিস্কার। এই পদ্ধতিতে ভুল হওয়ার সম্ভাবনা কম। এর কারণ খুব সহজে ভোল্টেজ আছে বা নেই, অন কিংবা অফ বলা যায় এবং অন্যান্য টেলিগ্রাফিক পদ্ধতির চেয়ে সহজ। ঠিক এই কারণেই আধুনিক কম্পিউটারগুলোতে বাইনারি সংখ্যা ব্যবহার করা হয়। ১৮৪৪ সালের ২৪ মে মোর্স সর্বপ্রথম একটি ইউ এস টেলিগ্রাফিক লিংকে মোর্স কোড ব্যবহার করে বার্তা পাঠান যা ছিল, What hath God wrought।
সুতরাং দেখা যাচ্ছে একটি টেক্সট তথ্যকে প্রথমে মোর্স কোড অর্থাৎ ডট-ড্যাশ রূপান্তরিত করা হয়, তারপর এটি তারের মাধ্যমে পাঠানো হয়, যেখানে থেকে আবার সেই ডট-ড্যাশ থেকে টেক্সটে রূপান্তরিত করা হয়।
এই তথ্য থেকে দেখা গেল যে, টেলিগ্রাফিক কমিউনিকেশনে মূলত কতগুলো সংকেত (মোর্স কোডের ক্ষেত্রে ডট-ড্যাশ) পাঠানো হয়, সেগুলো পরবর্তীতে অনুবাদ করে মূল তথ্যটি পুনরুদ্ধার করা হয়।


চিত্র : কোক ও হুইটস্টোন টেলিগ্রাফ

এবার আমরা একটু সামনে এগিয়ে করে মূল আলোচনায় চলে আসবো।
মূল ব্যাপার হচ্ছে, ক্যারেক্টার বা বর্ণ হলো যেকোনো লিখন পদ্ধতির মৌলিক একক। এদেরকে একটি বিশেষ আকৃতি বা ছবি দিয়ে প্রকাশ করা হয়। ইংরেজিতে এদের বলে glyph। তবে কম্পিউটার বর্ণ কিংবা ছবি এইরকম কোনো কিছুই মেমোরিতে স্টোর করতে পারে না। কম্পিউটার যা স্টোর করতে পারে তা হলো বিট (bit) যার অর্থ হতে পারে, yes অথবা no; true অথবা false; 1 অথবা 0। কম্পিউটার যেহেতু বিদ্যুতে চলে, সুতরাং আসলে বিট হলো একটি বৈদ্যুতিক পাল্স যা কখনো থাকে, কখনো থাকে না। আমাদের বোঝার সুবিধার্থে এগুলো 0 এবং 1 দিয়ে প্রকাশ করা হয়। তাহলে আমরা সহজ করে বলতে পারি যে, কম্পিউটার যা কিছু স্টোর বা কোনো কমিউনিকেশন লিংক দিয়ে ট্রান্সফার করে তা হলো কতগুলো বিট বা বাইনারি সংখ্যার সিকোয়েন্স বা ধারা।
এখন কতগুলো বাইনারি সিকোয়েন্সকে কোনো ক্যারেক্টার বা বর্ণতে প্রকাশ করতে হলে আমাদের কতগুলো নিয়মকানুনের দরকার হয়। এই নিয়মকানুনগুলোকে এনকোডিং স্কিম (Encoding Scheme) বলা হয়। যেমন,



চিত্র ১.৩৪: ASCII Encoding of 'java'

উপরের ছবিতে, java শব্দটিকে বাইনারি সিকোয়েন্সে রূপান্তরিত করা হয়েছে। এখানে 'a' এর বাইনারি হচ্ছে 01100001, 'b' এর বাইনারি 01100010, এভাবে 'c' এর বাইনারি 01100011। এভাবে ইংরেজি বর্ণমালার ২৬ টি বর্ণকে বাইনারিতে রূপান্তরিত করা হলে,

a -> 01100001
b -> 01100010
c -> 01100011
d -> 01100100
e -> 01100101
f -> 01100110
g -> 01100111
h -> 01101000
i -> 01101001
j -> 01101010
k -> 01101011
l -> 01101100
m -> 01101101
n -> 01101110
o -> 01101111
p -> 01110000
q -> 01110001
r -> 01110010
s -> 01110011
t -> 01110100
u -> 01110101
v -> 01110110
w -> 01110111
x -> 01111000
y -> 01111001
z -> 01111010

চিত্র: ইংরেজি বর্ণমালার ASCII Encoding


এখন যদি আমরা এই ২৬ টি বর্ণের বাইনারি ভ্যালু মনে রাখতে পারি, তাহলে খুব সহজেই বাইনারিতে যেকোনো লেখা পড়তে পারব, তাই নয় কি?

* এখন একটি প্রোগ্রাম লিখে ফেলুন যা একটি ক্যারেক্টার ইনপুট নেবে এবং সেটি যদি একটি আসকি ক্যারেক্টার হয়, তাহলে তা বাইনারিতে রূপান্তরিত করে কনসোলে প্রিন্ট করবে। 

উপরে যে পদ্ধতিতে ইংরেজি ভাষার বর্ণগুলোকে বাইনারিতে রূপান্তরিত করা হয়েছে, তাকে বলা হয় আসকি (ASCII)। এর পূর্ণরূপ হচ্ছে আমেরিকান স্ট্যান্ডার্ড কোড ফর ইনফরমেশন এক্সচেঞ্জ (American Standard Code for Information Interchange)। এই পদ্ধতিতে 0-0, ছোটো হাতের অক্ষর (a-z), বড় হাতের অক্ষর (A-Z), মুষ্টিমেয় যতিচিহ্ণ যেমন, ডলার চিহ্ন ($), এমপারস্যান্ড চিহ্ন (&) ইত্যাদি এবং এছাড়াও আরও কতগুলো কন্ট্রোল কোড যেমন, ক্যারেজ রিটার্ন (Carriage Return), লাইনফিড (Line Feed) ইত্যাদি নিয়ে মোট 128 টি ক্যারেক্টারের একটি টেবিল তৈরি করা হয়। এটি আসকি টেবিল নামে পরিচিত। গুগলে ASCII Table লিখে সার্চ করলেই টেবিলটি চলে আসবে। এই টেবিলে 128 ক্যারেক্টার থাকার কারণ হচ্ছে, প্রথম যে টেবিলটি তৈরি করা হয়েছিল, সেটি ছিল 7 বিটের। আমরা জানি যে, 7 বিট দিয়ে সর্বোচ্চ 128 () টি কম্বিনেশন তৈরী করা যায়, সুতরাং এতে সর্বোচ্চ 128 টি ক্যারেক্টার থাকতে পারে। পরবর্তীতে এই টেবিলকে সম্প্রসারিত করে 8 বিটে উন্নীত করা হয় এবং এতে 256 () টি ক্যারেক্টার রয়েছে।

http://www.ascii-code.com/ এই লিংকটিতে গেলে 256 টি ক্যারেক্টারের তালিকা দেখা যাবে।
এখন প্রশ্ন হতে পারে তাহলে আমরা কম্পিউটার স্ক্রিনে যে লেখা দেখছি তা কীভাবে দেখছি। এর উত্তর জানতে হলে আমাদের জানতে হবে ফন্ট কী।

ফন্ট (Font)
ফন্ট হলো এক ধরনের কম্পিউটার কোড যার মাধ্যমে কোনো একটি বর্ণকে কম্পিউটার স্ক্রিনে Glyph বা pictograph এর মাধ্যমে প্রদর্শন বা উপস্থান করা হয়। অর্থাৎ, ফন্ট হচ্ছে কোনো ক্যারেক্টার বা বর্ণের ছবি। এর মধ্যে ক্যারেক্টারের ও Glyph এর ম্যাপিং থাকে। যখন একটি ক্যারেক্টার ডিসপ্লে করার দরকার হয়, আমরা জানি যে, প্রত্যেকটি ক্যারেক্টারের একটি স্বতন্ত্র সংখ্যা থাকে, সেই সংখ্যা দিয়ে ফন্ট থেকে একটি Glyph বা ছবি বের করে আনা হয়। সহজ কথায় বলতে গেলে, ফন্ট মূলত কতগুলো Glyph এর অ্যারে যার ইনডেক্স হলো ক্যারেক্টারের সংখ্যা। একটি ফন্টের ভেতর আরও একাধিক ডেটা থাকতে পারে, যেমন, কীভাবে একটি ফন্টকে regular, italic, bold, uppercase, lowercase রূপান্তরিত করা যায় ইত্যাদি। এছাড়াও kerning (দুটি ক্যারেক্টারের মধ্যের দূরত্ব), hinting (কীভাবে বিভিন্ন সাইজের ফন্ট ডিসপ্লে বা আঁকা যায়), ligatures (অনেক সময় একাধিক glyph দিয়ে একটি ক্যারেক্টার তৈরি করতে হয়, যেমন, যুক্তবর্ণ) ইত্যাদি তথ্যও থাকে।
এবার আরও ভেতরে প্রবেশ করার আগে কতগুলো টার্ম জেনে নেওয়া যাক,

এনকোড (Encode)/ এনকোডিং (Encoding), ক্যারেক্টার সেট (Character Set) / কারসেট (charset), কোড পয়েন্ট (Code Point)

কম্পিউটার শুধুমাত্র বাইনারি সংখ্যা নিয়ে কাজ করে। কম্পিউটারে আমরা যে বর্ণমালা ব্যবহার করি, সেগুলোর প্রত্যেকটিকে একটি ইন্টিজার সংখ্যা (অঋণাত্বক বা নন-নেগেটিভ) দিয়ে ম্যাপিং করা হয়। ম্যাপিংয়ের অর্থ হচ্ছে, কোনো একটি ক্যারেক্টার বা বর্ণ একটি নির্দিষ্ট সংখ্যাকে নির্দেশ করে। যে নির্দিষ্ট ক্যারেক্টার বা বর্ণগুলোর এই ম্যাপিং করা হয়, তাদেরকে ক্যারেক্টার সেট (Character Set) / কারসেট (charset) বলা হয়। প্রত্যেকটি ক্যারেক্টারের যে ইন্টিজার ভ্যালু বা মান দেওয়া হয়, তাকে কোড পয়েন্ট (Code Point) বলা হয়। এই পুরো প্রক্রিয়াকে এনকোডিং (Encoding) বলা হয়। উদাহরণ, Latin capital letter A ('A') এর ASCII টেবিলে ইন্টিজারের ভ্যালু 65। বাইনারিতে এটি হয়ে যায়, 01000001। এখানে Latin capital letter A হচ্ছে আসকি ক্যারেক্টার সেটের একটি এনকোডেড ক্যারেক্টার এবং এর কোড পয়েন্ট হচ্ছে 01000001।
এখানে মনে রাখতে হবে যে, একই ক্যারেক্টারের কোড পয়েন্ট বিভিন্ন এনকোডিং স্কিমে বিভিন্ন হতে পারে এবং একই কোড পয়েন্ট বিভিন্ন এনকোডিং স্কিমে বিভিন্ন হতে পারে।

স্ট্রিং (String)
একাধিক ক্যারেক্টার এক সঙ্গে থাকলে তাদেরকে স্ট্রিং বলা হয়।

বাইনারি (Binary), অকটাল (Octal), ডেসিমাল (Decimal), হেক্সাডেসিামাল (Hexadecimal) / হেক্স (Hex)
আমরা জানি যে, যেকোনো সংখ্যাকে অনেকগুলো উপায়ে লেখা যায়। যেমন, 125 একটি ডেসিমাল সংখ্যা। এর বাইনারি হচ্ছে, 01111101। একইভাবে এর অকটাল, 175 এবং হেক্স বা হেক্সাডেসিমাল হচ্ছে 7D। সবগুলোর ভ্যালু যদিও এক কিন্তু হেক্স দৈর্ঘ্যে একটু ছোট এবং বাইনারি থেকে বেশি সহজে পড়া যায়। তাই অনেক সময় দেখা যাবে একই মানের সংখ্যা কোথাও হেক্স, আবার কোথাও ডেসিমাল দিয়ে প্রকাশ করা হচ্ছে।

আসকি টেবিল থেকে 128টি ক্যারেক্টার পাওয়া যায়। বর্ধিত আসকি (Extended ASCII) টেবিল থেকে যদিও 256 টি ক্যারেক্টার পাওয়া যায়, কিন্তু তা শুধুমাত্র ইংরেজি বর্ণমালার জন্য সীমাবদ্ধ। পৃথিবীতে নানা রকম ভাষা আছে, বাংলা (Bangla), ফরাসী (French), সুইডিস (Swidish), জার্মান (German) ইত্যাদি। এগুলোর বর্ণ আলাদা। সুতরাং দেখা যাচ্ছে আসকি এনকোডিং স্কিম দিয়ে এই ভাষার লেখাগুলোর বর্ণ ব্যবহার করা যাচ্ছে না। এই সমস্যা সমাধান করার জন্য অনেকেই নানা রকম এনকোডিং স্কিম তৈরি করেছে, যেমন- ISO-646, ISO-8859, UCS-2, UCS-4 CP47, Windows-1250, MIK, ISCII, TSCII ইত্যাদি।

এছাড়াও পৃথিবীতে আরও অনেক ভাষা রয়েছে- যেমন হিন্দি, আরবি, কোরিয়ান, রাশিয়ান ইত্যাদি। চাইনিজ এবং জাপানিজ ভাষায় হাজার হাজার বর্ণ রয়েছে যা কিনা 8 বিট দিয়ে প্রকাশ করা সম্ভব নয়। এই সমস্যা সমাধান করার জণ্যে পরবর্তীতে মাল্টি-বাইট এনকোডিং স্কিম (Multi-Byte Encoding Scheme) প্রবর্তন করা হয়। 8 বিটের পরিবর্তে যদি 16 বিট ব্যবহার করা হয়, তাহলে বা 65536 টি কম্বিনেশন পাওয়া যায়। এরকম একটি এনকোডিং স্কিম হলো, BIG-5। এ পদ্ধতিতে একটি বাইনারি সিকোয়েন্সের ধারাকে 8 বিট অন্তর অন্তর না ভেঙে 16 বিট পর পর ভেঙে সেই ব্লকের ভ্যালু নিয়ে কোড পেজ (Code Page) বা ক্যারেক্টার সেট থেকে বের করা হয়। এটি মূলত বেসিক চাইনিজ বর্ণগুলোর জন্য ব্যবহার করা হয়। এছাড়াও আরেকটি এনকোডিং সিস্টেম হলো, GB18030 যাতে বেসিক এবং সিম্প্লিফায়ড দুটো বর্ণমালায় রয়েছে।


ইউনিকোড (Unicode)
সুতরাং দেখা যাচ্ছে যে, বিভিন্ন ভাষার বর্ণ কম্পিউটার সিস্টেমে ব্যবহার করার জন্য বিভিন্ন রকম এনকোডিং সিস্টেম তৈরি করা হয়ছে। এগুলো অনেক সময় একটি আরেকটির সঙ্গে কাজ করে না। একই সঙ্গে একাধিক ভাষার বর্ণ এক সঙ্গে ব্যবহার করা কঠিন হয়ে পরে। এইসব সমস্যা সমাধান করার জন্য অবশেষে একটি এনকোডিং স্ট্যান্ডার্ড প্রবর্তন করা হয়, যার মাধ্যমে সবগুলো ভাষার বর্ণগুলো ব্যবহার যায়। এই এনকোডিং স্ট্যান্ডার্ডকে ইউনিকোড (Unicode) বলা হয়। তবে এখানে একটি বিষয় মনে রাখতে হবে যে, ইউনিকোড কোনো এনকোডিং স্কিম নয়। ইউনিকোড মূলত একটি টেবিল যা কিনা ক্যারেক্টারগুলো কোড পয়েন্ট নির্দেশ করে। এগুলোকে এনকোডিং করার জন্য একাধিক এনকোডিং স্কিম রয়েছে। ইউনিকোড কোড পয়েন্ট হেক্সাডেসিম্যালে লেখা হয়। এর কারণ হেক্সাডেসিম্যাল সংখ্যাগুলো ছোট। প্রত্যেকটি কোড পয়েন্টের আগে "U+" থাকে। যেমন, বাংলা ‘ক’ এর কোড পয়েন্ট হচ্ছে, U+0995। ‘খ’ এর কোড পয়েন্ট হচ্ছে, U+0996

ইউনিকোড টেবিলে মোট 1,114,112 কোড পয়েন্ট রয়েছে যেখানে সব ধরনের চিহ্ন, ইউরোপিয় (European), মধ্যপ্রাচ্যীয় (Middle Eastern), দক্ষিনীয় (Southern), প্রাচ্যীয় (Eastern), উত্তরীয় (Northern), পশ্চিমা (Western), প্রাগৈতিহাসিক (Pre-Historian) সব ধরনের ক্যারেক্টার রয়েছে। এর ফলে একটি ডকুমেন্টে যেকোনো ধরনের ক্যারেক্টার ব্যবহার করা যায়।
1,114,112 টি সংখ্যা রাখার জন্য ইউটনিকোডে 4 বাইট বা 32 বিট ব্যবহার করা হয়। তবে এখানে সমস্যা হচ্ছে যে, চাইনিজ বা জাপানিজ ক্যারেক্টারগুলো এনকোড করা জন্য বড় সংখ্যা দরকার হলেও সবগুলো বর্ণের জন্য 32 বিট দরকার পড়ে না। যেমন, 

'A' বর্ণটি এনকোড করা হলে তা হবে 00000000 00000000 00000000 01000001
'B' বর্ণটি এনকোড করা হলে তা হবে - 00000000 00000000 00000000 01000010 

যা কিনা যা দরকার তার দেখে অনেক বেশি। তাই ইউনিকোড কোড পয়েন্ট এনকোডিং অপটিমাইজ করার জন্য কতগুলো বিশেষ এনকোডিং স্কিম তৈরি করা হয়েছে। যেমন, UTF-32, UTF-16, UTF-8। UTF-32 এনকোডিং স্কিমে সবগুলো কোড পয়েন্ট 32 বিটে এনকোড করা হয়। UTF-16, UTF-8 এর এনকোডিং স্কিম একটু ভিন্ন। যদি কোনো বর্ণ বা ক্যারেক্টার এক বাইট বা 8 বিটে প্রকাশ করা যায়, তাহলে সেটি এক বাইট বা 8 বিটে এনকোড করবে এবং এর স্কিম হবে UTF-8। যদি 2 বাইট দরকার হয় তাহলে এটি 2 বাইট ব্যবহার করবে এবং স্কিম হবে UTF-16। এভাবে 4 বাইট পর্যন্ত ব্যবহার করবে। এতে করে অনেক কম জায়গায় ব্যবহার করা যায়। অন্যদিকে UTF-16 মাঝামাঝি, যা কিনা 2 বাইট থেকে শুরু করে 4 বাইট পর্যন্ত ব্যবহার করতে পারে।

character
Encoding
Bits
A
UTF-8
01000001
A
UTF-16
00000000 01000001
A
UTF-32
00000000 00000000 00000000 01000001

টেবিল: ইউনিকোড কোড পয়েন্ট এনকোডিং স্কিম

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