"রক্তাল্পতা মডেল" সমস্যাটি যেভাবে বর্ণনা করা হয়েছে তা এফপিতে তেমন ভাল অনুবাদ করে না। প্রথমে এটি যথাযথভাবে সাধারণীকরণ করা দরকার। এটির হৃদয়ে, অ্যানিমিক মডেল এমন একটি মডেল যা সঠিকভাবে কীভাবে এটি ব্যবহার করতে হয় সে সম্পর্কে জ্ঞান রয়েছে যা মডেল নিজেই আবৃত হয় না। পরিবর্তে, সেই জ্ঞান সম্পর্কিত পরিষেবাদির স্তূপের চারদিকে ছড়িয়ে পড়ে। এই পরিষেবাগুলি কেবলমাত্র মডেলের ক্লায়েন্ট হওয়া উচিত , তবে রক্তাল্পতার কারণে তারা এর জন্য দায়ী হন। উদাহরণস্বরূপ, এমন একটি Account
শ্রেণীর কথা বিবেচনা করুন যা অ্যাকাউন্ট সক্রিয় বা নিষ্ক্রিয় করতে ব্যবহার করা যাবে না এমনকি কোনও অ্যাকাউন্টের বিষয়ে তথ্য অনুসন্ধানের জন্য যদি কোনও AccountManager
শ্রেণীর মাধ্যমে পরিচালনা না করা হয় । অ্যাকাউন্টটি কোনও বাহ্যিক ব্যবস্থাপক শ্রেণীর জন্য নয়, এটিতে প্রাথমিক ক্রিয়াকলাপগুলির জন্য দায়বদ্ধ হওয়া উচিত।
ফাংশনাল প্রোগ্রামিংয়ে, একই ধরণের সমস্যা উপস্থিত থাকে যখন ডেটা টাইপগুলি তাদের মডেল হওয়ার কথা সঠিকভাবে উপস্থাপন করে না। ধরুন আমাদের ব্যবহারকারীর আইডি উপস্থাপনকারী একটি প্রকারের সংজ্ঞা দেওয়া দরকার। "রক্তাল্পতা" সংজ্ঞাটি বলতে চাইবে যে ব্যবহারকারী আইডিগুলি স্ট্রিং। এটি প্রযুক্তিগতভাবে সম্ভব, তবে বিশাল সমস্যার মধ্যে চলে কারণ ব্যবহারকারী আইডিগুলি স্বেচ্ছামূলক স্ট্রিংয়ের মতো ব্যবহার করা হয় না । সেগুলি বোঝাতে বা তাদের সাবস্ট্রিংগুলি টুকরো টুকরো টুকরো টুকরো টিকতে পারে না, ইউনিকোডের সত্যিকার অর্থে কিছু হওয়া উচিত নয় এবং এগুলি কঠোর চরিত্র এবং বিন্যাসের সীমাবদ্ধতার সাথে ইউআরএল এবং অন্যান্য প্রসঙ্গে সহজেই এম্বেডযোগ্য হতে হবে।
এই সমস্যাটি সমাধান করা সাধারণত কয়েকটি পর্যায়ে ঘটে। একটি সাধারণ প্রথম কাটাটি বলতে হয় "আচ্ছা, UserID
এটিকে একটি স্ট্রিংয়ের সমতুল্য উপস্থাপন করা হয় তবে সেগুলি বিভিন্ন ধরণের এবং আপনি যেখানে অন্যটির প্রত্যাশা করেন সেখানে একটি ব্যবহার করতে পারবেন না।" হাস্কেল (এবং কিছু অন্যান্য টাইপযুক্ত কার্যকরী ভাষা) এর মাধ্যমে এই বৈশিষ্ট্যটি সরবরাহ করে newtype
:
newtype UserID = UserID String
এই সংজ্ঞায়িত UserID
ফাংশন যা প্রদত্ত String
যে একটি মান নির্মান মত চিকিত্সা একটি UserID
টাইপ সিস্টেম দ্বারা, কিন্তু যা এখনও শুধু একটি হল String
রানটাইম এ। এখন ফাংশনগুলি ঘোষণা করতে পারে যে তাদের UserID
একটি স্ট্রিংয়ের পরিবর্তে প্রয়োজন ; ব্যবহার UserID
গুলি যেখানে আপনি পূর্বে দুই concatenating কোড বিরুদ্ধে স্ট্রিং রক্ষীদের ব্যবহার করছেন সেটি UserID
গুলি একসঙ্গে। টাইপ সিস্টেমটি গ্যারান্টি দেয় যা ঘটতে পারে না, কোনও পরীক্ষার প্রয়োজন হয় না।
দুর্বলতা এখানে এই কোডটি এখনও যে কোন অবাধ নিতে পারেন String
মত "hello"
এবং গঠন করা UserID
তা থেকে। পরবর্তী পদক্ষেপগুলির মধ্যে একটি "স্মার্ট কনস্ট্রাক্টর" ফাংশন তৈরি করা অন্তর্ভুক্ত যা একটি স্ট্রিং দেওয়ার পরে কিছু আক্রমণকারী পরীক্ষা করে এবং UserID
তারা সন্তুষ্ট হলে কেবল একটি প্রদান করে । তারপরে "বোবা" UserID
কনস্ট্রাক্টরটিকে বেসরকারী করে তোলা হয়েছে যদি কোনও ক্লায়েন্ট চায় UserID
তাদের অবশ্যই স্মার্ট কনস্ট্রাক্টর ব্যবহার করতে হবে , যার ফলে ত্রুটিযুক্ত ইউজারআইডিগুলি অস্তিত্বে আসতে বাধা দেয়।
এমনকি আরও পদক্ষেপগুলি UserID
ডেটা প্রকারটিকে এমনভাবে সংজ্ঞায়িত করে যে কেবলমাত্র সংজ্ঞা দ্বারা খণ্ডিত বা "অনুপযুক্ত" একটি তৈরি করা অসম্ভব । উদাহরণস্বরূপ, UserID
সংখ্যার তালিকা হিসাবে একটি সংজ্ঞা দেওয়া :
data Digit = Zero | One | Two | Three | Four | Five | Six | Seven | Eight | Nine
data UserID = UserID [Digit]
নির্মাণ করারও UserID
ডিজিটের একটি তালিকা প্রদান করা আবশ্যক। এই সংজ্ঞাটি দেওয়া হয়েছে, এটি দেখা তুচ্ছ যে এটি কোনওরকমই অসম্ভব যে এটি UserID
কোনও ইউআরএলে প্রতিনিধিত্ব করা যায় না। মধ্যে Haskell ভালো ডিফাইনিং ডেটা মডেল প্রায়ই মত উন্নত ধরনের সিস্টেম বৈশিষ্ট্য সহায়তায় হয় ডেটা প্রকারের এবং জেনারেলাইজড বীজগাণিতিক ডেটা প্রকার (GADTs) , যা টাইপ সিস্টেম এবং সংজ্ঞায়িত আপনার কোড সম্পর্কে আরো invariants প্রমাণ করার অনুমতি দেয়। আচরণ থেকে ডেটা যখন ডিউপলড হয় তখন আপনার ডেটা সংজ্ঞা কেবলমাত্র আপনাকে আচরণ প্রয়োগ করতে হবে।