Якщо функція "чиста", я не бачу проблем. Чиста функція працює лише у вхідних параметрах і забезпечує результат, заснований на цьому. Це не залежить від будь-якого глобального стану чи зовнішнього контексту.
Якщо я дивлюсь на приклад власного коду:
public class Class1
{
public static string GetSomeString()
{
// do something
}
}
Ця функція не приймає жодних параметрів. Таким чином, він, ймовірно, не є чистим (єдиною чистою реалізацією цієї функції було б повернення константи). Я припускаю, що цей приклад не є репрезентом вашої реальної проблеми, я просто вказую, що це, мабуть, не є чистою функцією.
Давайте візьмемо інший приклад:
public static bool IsOdd(int number) { return (number % 2) == 1; }
Немає нічого поганого в тому, що ця функція є статичною. Ми могли навіть перетворити це на функцію розширення, що дозволяє клієнтському коду стати ще читабельнішим. Функції розширення - це в основному лише особливий вид статичних функцій.
Теластин правильно згадує одночасність як потенційну проблему зі статичними членами. Однак, оскільки ця функція не використовує загальний стан, тут немає проблем з одночасністю. Тисяча ниток може викликати цю функцію одночасно без жодних проблем одночасності.
У .NET рамках методи розширення існують досить давно. LINQ містить безліч функцій розширення (наприклад, Enumerable.Where () , Enumerable.First () , Enumerable.Single () тощо). Ми не вважаємо це поганим, чи не так?
Тестування одиниць часто може отримати користь, коли код використовує змінні абстракції, що дозволяє тесту блоку замінити системний код тестовим подвійним. Статичні функції забороняють цю гнучкість, але це головне важливо на межах архітектурного рівня, де ми хочемо замінити, наприклад, фактичний рівень доступу до даних фальшивим рівнем доступу до даних.
Однак, коли пишемо тест для об'єкта, який веде себе по-різному, залежно від того, чи якесь число непарне чи парне, нам насправді не потрібно мати можливість замінити IsOdd()
функцію альтернативною реалізацією. Так само я не бачу, коли нам потрібно надати іншу Enumerable.Where()
реалізацію для тестування.
Тож давайте вивчимо читабельність коду клієнта для цієї функції:
Варіант a (з функцією, оголошеною як метод розширення):
public void Execute(int number) {
if (number.IsOdd())
// Do something
}
Варіант b:
public void Execute(int number) {
var helper = new NumberHelper();
if (helper.IsOdd(number))
// Do something
}
Функція статичного (розширення) робить перший фрагмент коду набагато більш читабельним, а читабельність має велике значення, тому використовуйте статичні функції, де це доречно.