آخر مرة كتبت أن أسماء الأشياء لها أهمية كبيرة ، وأنها تحتاج إلى اختيارها بعناية مع الاهتمام بالتفاصيل. اسم سيء يخيف ولا يسمح لفهم جوهر ما يحدث. ولكن ما هو جوهر هذا؟
من الصعب تقييم البطل دون فهم "إحصائياته" و "قدراته" . ما يمكنه وما هو قادر عليه هو المستوى التالي من الصعوبة التي يجب علينا الغوص فيها. لا يكفي أن تعكس الملجأ الداخلي للكائن بمساعدة الاسم الدقيق ، فأنت بحاجة أيضًا إلى التأكد من أن هذا هو الملاذ نفسه ، وليس الإسطبلات من الحروف.
حول هذا - في المقال.
جدول دورة المحتويات
- الكائنات
- الإجراءات والخصائص
- الرمز كنص
الإجراءات
الهجمات الشخصية ، يدافع ، يتهرب ، يطلق النار من القوس ، ويستخدم نوبات ، ويلوح شفرة. يعكس الاسم الكائن ، ولكن الكائن نفسه يتحرك ، كرد فعل ، في العمل. خلاف ذلك ، كنا نتحدث عن الجداول في Excel.
في C # ، الإجراءات هي الطرق والوظائف. ولنا: الأفعال ، ذرات الحركة الكلامية. الأفعال تتحرك الوقت ، بسببها الكائنات موجودة وتتفاعل. عندما يكون هناك تغيير - يجب أن يكون هناك فعل.
اضعي
من بين كل التغييرات ، تكون المهمة أقل من كل المنقولات. وهو يصف بدقة وبصورة رياضية ماهية الكميات وما هي مساوية لها ، ولكنه لا يوصل الحياة والنشاط إلى نص ، كما تفعل الأفعال.
على سبيل المثال ، هناك IPullRequest
مع خاصية Status
، والتي يمكن IPullRequest
أو IPullRequest
أو Merged
. يمكنك كتابة pullRequest.Status = Status.Declined
، ولكن هذا هو نفسه قول "تعيين طلب التجمع إلى الحالة الملغاة" ، أمر حتمي. أقوى بكثير هو pullRequest.Decline()
، وبالتالي ، pullRequest.Approve()
، pullRequest.Merge()
.
الفعل النشط هو الأفضل من واضع ، ولكن ليس كل الأفعال هي.
صوت سلبي
PerformPurchase
، DoDelete
، MakeCall
.
كما هو الحال في HeroManager
يتم إخفاء اسم مهم من قبل Manager
بلا معنى ، لذلك في PerformMigration
- Perform
. بعد كل شيء ، على قيد الحياة أكثر - مجرد Migrate
!
تعمل الأفعال النشطة على تحديث النص: ليس "ضرب" ، ولكن "ضرب" ؛ ليس "صنع تأرجح" ، ولكن "لوح" ؛ ليس "اتخذ قرارًا" ، ولكن " اتخذ " . حتى في التعليمات البرمجية: PerformApplication
→ Apply
؛ DoDelete
→ Delete
؛ PerformPurchase
→ Purchase
، Buy
. (لكن DealDamage
استقرت ، على الرغم من أنه في حالات نادرة قد يكون الهدف من Attack
.)
تجنب الصوت السلبي ، نقوم بتطوير القصة ونقل الشخصيات ، لكننا بحاجة أيضًا إلى التأكد من أن الفيلم لا يظهر باللونين الأبيض والأسود.
أفعال قوية
بعض الكلمات تنقل ظلال المعنى أفضل من غيرها. إذا كتبت "شرب كوبًا من الماء" ، فسيكون ذلك بسيطًا وواضحًا. لكن "استنزف كوبًا من الماء" - مجازيًا ، أقوى.
لذلك يمكن التعبير عن التغيير الصحي للاعب من خلال player.Health = X
أو player.Health = X
، ولكن المزيد من player.RestoreHealth
الخلابة هي player.RestoreHealth
.
أو ، على سبيل المثال ، نحن نعرف Stack
ليس عن طريق Add/Remove
، ولكن عن طريق Push/Pop
.
أفعال قوية ونشطة تشبع الكائن مع السلوك ، إذا لم تكن محددة للغاية.
أجزاء زائدة عن الحاجة
كما هو الحال مع ManualResetEvent
، فكلما اقتربنا من الحدود الداخلية التقنية لـ .NET ، والتي ستكون معقدة وسيكون من الجيد التعبير عنها ببساطة ، كلما كانت تفاصيل وتجاوزات واجهة برمجة التطبيقات أكثر ثراءً.
يحدث أنك تحتاج إلى القيام ببعض الأعمال في سلسلة رسائل أخرى ، ولكن حتى لا تهتم بإنشاء هذا البرنامج وإيقافه. في C # هناك ThreadPool
لهذا. هنا فقط هو بسيط "القيام بالعمل" هنا - QueueUserWorkItem
! ما نوع عنصر العمل ( WorkItem
) وما يمكن أن يكون ، إن لم يكن المستخدم ( User
) ، غير واضح. سيكون أسهل بكثير - ThreadPool.Run
أو ThreadPool.Execute
.
مثال آخر إن التذكر ومعرفة وجود تعليمات مقارنة ومبادلة ذرية (CAS) أمر جيد ، ولكن نقلها نظيفًا إلى الكود ليس هو الحل الأفضل. Interlocked.CompareExchange(ref x, newX, oldX)
أدنى من Interlocked.CompareExchange(ref x, newX, oldX)
Atomically.Change(ref x, from: oldX, to: newX)
(باستخدام المعلمات المسماة).
الكود ليس دكتوراه في العمل مع كمبيوتر الكم ، وليس تطبيقًا على العمليات الحسابية الرياضية ، لكن القارئ في بعض الأحيان لا يهتم تمامًا بما تسمى الإرشادات ذات المستوى المنخفض. الاستخدام اليومي مهم.
تكرار
UsersRepository.AddUser
، Benchmark.ExecuteBenchmark
، AppInitializer.Initialize
، UniversalMarshaller.Marshal
، Logger.LogError
.
كما قلت في الجزء الأخير ، التكرار يؤدي إلى تآكل المعنى ، ويضغط المساحة.
ليس UsersRepository.AddUser
، لكن UsersRepository.Add
؛ ليس Directory.CreateDirectory
، ولكن Directory.Create
؛ ليس HttpWebResponse.GetResponseStream
، ولكن HttpWebResponse.Stream
؛ ليس Logger.LogError
، ولكن Log.Error
.
القمامة الجميلة
Check
كلمة متعددة الجوانب. يمكن CheckHasLongName
إما إرجاع bool
أو رمي استثناء إذا كان لدى المستخدم اسم طويل جدًا. الأفضل هو bool HasLongName
أو void EnsureHasShortName
. حتى قابلت CheckRebootCounter
، والتي ... في الداخل ، CheckRebootCounter
تشغيل IIS!
Enumerate
- من نفس السلسلة. هناك طريقة Directory.EnumerateDirectories(path)
في .NET: لسبب ما ، يتم تحديد أن المجلدات سيتم سردها ، على الرغم من أن path.Directories()
Directories.Of(path)
أو path.Directories()
.
Calc
كثير من الأحيان يتم تقليل Calculate
- Calculate
، على الرغم من أنها تبدو أكثر مثل رواسب الكالسيوم.
Proc
هو اختصار آخر يتوهم للعملية.
الكلمات Base
، Impl
، Internal
، Raw
الطفيلية التي تشير إلى تعقيد الأشياء.
في المجموع
مرة أخرى ، سوف يلاحظ القارئ المهتم ، كل ذلك يعود إلى التبسيط ، وتشبيه الكلام الطبيعي ، والنصائح نفسها لا تتعلق إلى حد كبير بالكود فحسب ، بل بالكتابة بشكل عام. باستخدامهم ، يقوم المطور بتلميع كل من الرمز كنص ونص ، مع السعي للحصول على عرض تقديمي شفاف وسهل ، من أجل البساطة.
الآن وبعد أن اكتشفنا الحركة و "المؤثرات الخاصة" ، دعونا نلقي نظرة على كيفية وصف العلاقات بين الكائنات.
الخصائص
الطابع لديه الصحة ومانا. العناصر الموجودة في سلة التسوق ؛ يتكون النظام الشمسي من كواكب. الكائنات لا تعمل فقط من دون أنانية ، ولكن أيضًا تتعلق: هرميًا (سلف وريث) ، تكوينيًا (جزء صحيح) ، مكانيًا (عنصر تخزين) ، إلخ.
في C # ، الخصائص والعلاقات هي طرق (عادة ما تبدأ بـ Get
) ، getters (خصائص ذات نص get
معين) ، والحقول. ولكن بالنسبة لنا هو: الكلمات - الإضافات التي تعبر عن انتماء كائن إلى آخر. على سبيل المثال ، يتمتع اللاعب بصحة - Player.Health
، والذي يتوافق تقريبًا مع "صحة اللاعب" الإنجليزية.
ما هو الأكثر حيرة اليوم هو أساليب العمل وأساليب الملكية.
الفعل بدلا من الاسم
GetDiscount
، CalculateDamage
، FetchResult
، ComputeFov
، CreateMap
.
يسمع التسويات في كل مكان: يجب أن تبدأ الطرق بالأفعال. نادراً ما ترى أي شخص يشكك: هل هذا صحيح حقًا؟ بعد كل شيء ، لا يمكن أن يكون هناك فرق كبير بين Player.Health
و Player.Health()
. دع السجلات تكون مختلفة في سياقها ، فهي تعني نفس الشيء.
لنفترض أنه في IUsersRepository
، من IUsersRepository
بعض GetUser(int id)
. لماذا ، لتمثيل المستخدم ، فكر في نوع من الإيصال ( Get
)؟ سيكون أكثر دقة - User(int id)
!
وحقا: لا FetchResult()
، ولكن Result()
؛ ليس GetResponse()
، لكن Response()
؛ ليس CalculateDamage()
، ولكن Damage()
.
نقاش DDD واحد يعطي مثالاً على الكود "الجيد": DiscountCalculator
مع طريقة CalculateDiscountBy(int customerId)
. ليس هناك فقط تكرار متماثل على الوجه - DiscountCalculator.CalculateDiscount
، فقد حددوا أيضًا أنه يتم حساب الخصم. وماذا يسأل المرء ماذا يفعل معها؟
سيكون أقوى من الانتقال من الكيان نفسه - Discount
باستخدام static decimal Of(Customer customer, Order order)
للاتصال _discountCalculator.CalculateDiscountBy(customerId)
من Discount.Of(customer, order)
- هو أبسط من _discountCalculator.CalculateDiscountBy(customerId)
، ويتوافق مع لغة واحدة.
أحيانًا ، عند حذف الفعل ، نفقد شيئًا ، كما يقول ، في CreateMap()
: قد لا يكون الاستبدال المباشر بـ Map()
كافيًا. الحل الأفضل هو NewMap()
: مرة أخرى ، الكائن في الرأس ، وليس الإجراء.
استخدام الأفعال الفارغة الفارغة هو سمة لثقافة عفا عليها الزمن وعاجلة ، حيث تكون الخوارزمية أساسية وتتقدم على المفهوم. ستجد غالبًا "شفرة تم تخفيفها" من "شفرة صلابة" . لكن أسلوب الكتب عن جيمس بوند غير مناسب لوصف المشهد. حيث لا توجد حركة ، لا يوجد مكان للفعل.
آخر
الخصائص والأساليب التي تعبر عن العلاقات بين الأشياء هي أيضًا كائنات ، وبالتالي ، فإن ما سبق ذكره في كثير من النواحي ينطبق عليها.
على سبيل المثال ، التكرار في الخصائص: ليس Thread.CurrentThread
، لكن Thread.Current
؛ ليس Inventory.InventoryItems
. عناصر Inventory.InventoryItems
، ولكن Inventory.Items
. Inventory.Items
، الخ.
في المجموع
لا يتم الخلط بين الكلمات البسيطة والمفهومة ، وبالتالي لا يتم الخلط بين الكود الذي يتكون منها. في الكتابة ، من المهم بنفس القدر أن تكتب بسهولة: تجنب حروف الجر السلبي ، وفرة من الظروف والصفات ، التكرار ، للأفعال تفضل الفعل على الاسم. أحد الأمثلة المعروفة: "لقد هز رأسه برأسه ، ووافق" ، بدلاً من " برأس برأسه" ، وأحدث إبتسامة ، وأذكر QueueUserWorkItem
.
يختلف النص الموجود في الكود أيضًا في الحالة الأولى التي ستدفع فيها إذا كان المنزل واقفًا ، ويغرق في أشعة الشمس المشرقة ؛ في الثانية - إذا كان المنزل واقفا ؛ ولكن الأمر يستحق التذكر: يجب أن يقف المنزل ، وليس العصي من المساعدين.
في أول مقالتين من السلسلة ، أردت أن أوضح مدى أهمية العمل ليس فقط على الخوارزمية ، ولكن أيضًا على الكلمة ؛ كيف تحدد الأسماء محتوى ما يسمى ؛ كيف رمز زائدة ومضاعفة يحرك القارئ بعيدا.
جنبا إلى جنب مع هذا ، الأسماء الجيدة هي مجرد ملاحظات. للعب ، يجب أن تكون مكتوبة وتجسيدها في الموسيقى. سوف أخبركم أكثر في المقال التالي ، النهائي.