Стратегії та практичні посібники з оптимізації витрат на газ для смартконтрактів Ethereum

Практичний посібник з оптимізації витрат на газ для смартконтрактів Ethereum

Газові витрати на основній мережі Ethereum завжди були складною проблемою, особливо під час завантаження мережі. У пікові години користувачі часто змушені платити надзвичайно високі комісії за транзакції. Тому оптимізація витрат на газ на етапі розробки смартконтрактів є надзвичайно важливою. Оптимізація споживання газу не лише може ефективно знизити витрати на транзакції, але й підвищити ефективність транзакцій, надаючи користувачам більш економічний та ефективний досвід використання блокчейну.

У цій статті буде розглянуто механізм Gas-кошту Ethereum Virtual Machine (EVM), основні концепції оптимізації Gas-кошту та найкращі практики оптимізації Gas-кошту під час розробки смартконтрактів. Сподіваємось, що цей матеріал надихне розробників і надасть практичну допомогу, а також допоможе звичайним користувачам краще зрозуміти, як працюють Gas-витрати EVM, щоб разом протистояти викликам у блокчейн-екосистемі.

Ethereum смартконтракти Gas оптимізація десять найкращих практик

Вступ до механізму плати за газ EVM

У мережах, сумісних з EVM, "Gas" є одиницею, що використовується для вимірювання обчислювальної потужності, необхідної для виконання певних операцій.

У структурі EVM витрати газу поділяються на три частини: виконання операцій, виклики зовнішніх повідомлень, а також читання та запис у пам'ять і сховище.

Оскільки виконання кожної транзакції потребує обчислювальних ресурсів, стягується певна плата для запобігання безкінечним циклам і атакам відмови в обслуговуванні ( DoS ). Плата, необхідна для завершення транзакції, називається "Gas плата".

З моменту вступу в силу хардфорка Лондон EIP-1559(), плата за газ розраховується за наступною формулою:

Газовий збір = одиниці газу, що використовуються * (базовий збор + пріоритетний збор)

Базовий збір буде знищено, а пріоритетні збори використовуватимуться як стимул, щоб заохотити валідаторів додавати транзакції до блокчейну. Встановлення вищого пріоритетного збору під час відправлення транзакції може підвищити ймовірність включення транзакції в наступний блок. Це схоже на "чайові", які користувачі платять валідаторам.

1.Розуміння оптимізації Gas в EVM

Коли смартконтракт компілюється за допомогою Solidity, контракт перетворюється на ряд "операційних кодів", тобто opcodes.

Будь-яка частина коду операцій (, така як створення смартконтракту, виконання викликів повідомлень, доступ до зберігання рахунків та виконання операцій на віртуальній машині ) має визнану вартість споживання Gas, ці витрати зафіксовані в жовтій книзі Ethereum.

Після кількох змін EIP, деякі з кодів операцій мають відкориговану вартість Gas, що може відрізнятися від зазначеного в жовтій книзі.

2.Основні концепції оптимізації газу

Основна ідея оптимізації Gas полягає в пріоритетному виборі операцій з високою вартісною ефективністю на блокчейні EVM, уникаючи дорогих за вартістю операцій.

У EVM, наступні операції мають нижчу вартість:

  • Читання та запис змінних пам'яті
  • Читання констант та незмінних змінних
  • Читати та записувати локальні змінні
  • Зчитування змінної calldata, наприклад масиву calldata та структур.
  • Виклик внутрішньої функції

Високовартісні операції включають:

  • Читання та запис змінних стану, що зберігаються в контракті
  • Виклик зовнішніх функцій
  • Циклічна операція

Ethereum смартконтракти Gas оптимізація десять найкращих практик

Оптимізація витрат на газ EVM: найкращі практики

На основі вищезазначених основних концепцій, ми підготували для спільноти розробників список найкращих практик оптимізації Gas-кошту. Дотримуючись цих практик, розробники можуть знизити споживання Gas-кошту смартконтрактів, знизити витрати на транзакції та створити більш ефективні та зручні для користувачів програми.

1. Спробуйте зменшити використання пам'яті.

У Solidity, Storage( зберігання) є обмеженим ресурсом, його витрати газу значно вищі, ніж у Memory( пам'яті). Кожного разу, коли смартконтракт читає або записує дані зі зберігання, це призводить до високих витрат газу.

Згідно з визначенням з жовтої книги Ethereum, вартість операцій з пам'яттю перевищує вартість операцій з зберігання більш ніж у 100 разів. Наприклад, команди OPcodesmload та mstore споживають лише 3 одиниці газу, тоді як операції з зберігання, такі як sload та sstore, навіть у найкращих умовах, коштують щонайменше 100 одиниць.

Обмеження методів використання зберігання включає:

  • Зберігати непостійні дані в пам'яті
  • Зменшити кількість змін у зберіганні: зберігати проміжні результати в пам'яті, а після завершення всіх обчислень призначати результати змінним зберігання.

Ethereum смартконтрактів Gas оптимізації десять найкращих практик

2. Упаковка змінних

Кількість слотів зберігання (, що використовуються у смартконтрактах, а також спосіб, яким розробники відображають дані, значно вплине на витрати на газ.

Компілятор Solidity під час компіляції упаковує послідовні змінні зберігання і використовує 32-байтовий слот зберігання як основну одиницю зберігання змінних. Упаковка змінних означає раціональне розташування змінних, щоб кілька змінних могли вміститися в одному слоті зберігання.

Завдяки цьому коригуванню деталі, розробники можуть зекономити 20 000 одиниць Gas. ) Зберігання невикористаного сховища потребує 20 000 Gas (, але тепер потрібно лише два сховища.

Оскільки кожен слот для зберігання споживає газ, упаковка змінних оптимізує використання газу, зменшуючи кількість необхідних слотів для зберігання.

![Ethereum смартконтрактів Gas оптимізації десять найкращих практик])https://img-cdn.gateio.im/webp-social/moments-30f0bc370a7b9ca65f3d623c31262b76.webp(

) 3. Оптимізація типів даних

Змінна може бути представлена різними типами даних, але різні типи даних мають різну вартість операцій. Вибір відповідного типу даних допомагає оптимізувати використання газу.

Наприклад, у Solidity цілі числа можуть бути поділені на різні розміри: uint8, uint16, uint32 тощо. Оскільки EVM виконує операції в 256 біт, використання uint8 означає, що EVM спочатку має перетворити його на uint256, а це перетворення додатково споживає Gas.

Окремо, тут використання uint256 дешевше, ніж uint8. Однак, якщо використовувати оптимізацію пакування змінних, яку ми раніше пропонували, то це буде по-іншому. Якщо розробник зможе упакувати чотири uint8 змінні в один слот пам'яті, то загальна вартість їх ітерації буде нижчою, ніж у чотирьох uint256 змінних. Таким чином, смартконтракт зможе читати і записувати один слот пам'яті і за одну операцію помістити чотири uint8 змінні в пам'ять/сховище.

![Ethereum смартконтракти Gas оптимізації десять найкращих практик]###https://img-cdn.gateio.im/webp-social/moments-995905cb414526d4d991899d0c2e6443.webp(

) 4. Використовуйте змінні фіксованого розміру замість динамічних змінних

Якщо дані можна контролювати в межах 32 байт, рекомендується використовувати тип даних bytes32 замість bytes або strings. Загалом, змінні фіксованого розміру споживають менше газу, ніж змінні змінного розміру. Якщо довжину байтів можна обмежити, намагайтеся вибрати мінімальну довжину від bytes1 до bytes32.

![Ethereum смартконтрактів Gas оптимізації десятка найкращих практик]###https://img-cdn.gateio.im/webp-social/moments-55fcdb765912ef9cd238c46b1d248cff.webp(

) 5. Відображення та масиви

Список даних у Solidity можна представити двома типами даних: масивами ###Arrays ( та відображеннями )Mappings (, але їхній синтаксис і структура кардинально різні.

В більшості випадків мапи є більш ефективними та менш витратними, але масиви мають ітеративність і підтримують упаковку типів даних. Тому рекомендується при управлінні списками даних віддавати перевагу мапам, якщо немає потреби в ітерації або їх можна оптимізувати за рахунок упаковки типів даних для зменшення витрат Gas.

![Оптимізація Gas для смартконтрактів Ethereum: десять найкращих практик])https://img-cdn.gateio.im/webp-social/moments-5f3d7e103e47c886f50599cffe35c707.webp(

) 6. Використання calldata замість memory

Змінні, оголошені в параметрах функції, можуть зберігатися в calldata або memory. Основна різниця між ними полягає в тому, що memory можна змінювати функцією, тоді як calldata є незмінним.

Запам'ятайте цей принцип: якщо параметри функції є тільки для читання, слід віддавати перевагу використанню calldata, а не memory. Це дозволяє уникнути непотрібних операцій копіювання з calldata функції в memory.

![Ethereum смартконтракти Gas оптимізація десяти найкращих практик]###https://img-cdn.gateio.im/webp-social/moments-9c566626ab499ef65d6f5089a2876ad3.webp(

) 7. Намагайтеся використовувати ключові слова Constant/Immutable якомога більше

Постійні/незмінні змінні не зберігаються в сховищі контракту. Ці змінні обчислюються під час компіляції і зберігаються в байт-коді контракту. Тому, в порівнянні зі сховищем, вартість їх доступу набагато нижча, рекомендується використовувати ключові слова Constant або Immutable якомога більше.

![Ethereum смартконтракти Gas оптимізації десять найкращих практик]###https://img-cdn.gateio.im/webp-social/moments-c0701f9e09280a1667495d54e262dd2f.webp(

) 8. Використовуйте Unchecked, щоб забезпечити, що переповнення / недоповнення не відбудеться

Коли розробники можуть бути впевнені, що арифметичні операції не призведуть до переповнення або недостатності, можна використовувати ключове слово unchecked, введене в Solidity v0.8.0, щоб уникнути зайвих перевірок на переповнення або недостатність, тим самим заощаджуючи витрати на Gas.

Крім того, компілятор версії 0.8.0 та вище більше не потребує використання бібліотеки SafeMath, оскільки компілятор сам по собі вбудував функції захисту від переповнення та недостатності.

![Ethereum смартконтракти Gas оптимізація десять кращих практик]###https://img-cdn.gateio.im/webp-social/moments-a823fb7761aafa6529a6c45304e0314b.webp(

) 9. Оптимізатор

Код модифікатора вбудовується у змінену функцію, і щоразу, коли використовується модифікатор, його код копіюється. Це збільшує розмір байткоду та підвищує споживання Gas.

Шляхом перетворення логіки в внутрішню функцію _checkOwner###(, дозволяється повторно використовувати цю внутрішню функцію в модифікаторах, що може зменшити розмір байт-коду та знизити витрати на Gas.

![Ethereum смартконтракти Gas оптимізація десять найкращих практик])https://img-cdn.gateio.im/webp-social/moments-839b91e2f02389949aa698d460a497d8.webp(

) 10. Оптимізація короткого замикання

Для || та && операторів логічні операції підлягають короткому оцінюванню, тобто якщо перша умова вже може визначити результат логічного виразу, друга умова не буде оцінюватися.

Щоб оптимізувати витрати на газ, слід розміщувати умови з низькими витратами на обчислення на початку, що може дозволити пропустити обчислення з високими витратами.

![Ethereum смартконтракти Gas оптимізація десять кращих практик]###https://img-cdn.gateio.im/webp-social/moments-a141884dcdcdc56faff12eee2601b7b7.webp(

Додаткові загальні поради

) 1. Видалити непотрібний код

Якщо в контракті є невикористані функції або змінні, рекомендується їх видалити. Це найпряміший спосіб зменшити витрати на розгортання контракту та зберегти обсяг контракту малим.

Ось кілька корисних порад:

  • Використовуйте найефективніший алгоритм для обчислень. Якщо у контракті безпосередньо використовуються результати певних обчислень, то слід прибрати ці надмірні обчислювальні процеси. По суті, будь-які невикористані обчислення повинні бути видалені.

  • У Ethereum розробники можуть отримувати винагороду за Gas, звільняючи місце для зберігання. Якщо змінна більше не потрібна, її слід видалити за допомогою ключового слова delete або встановити на значення за замовчуванням.

  • Оптимізація циклів: уникайте витратних операцій з циклами, об'єднуйте цикли, де це можливо, та виводьте повторні обчислення з тіла циклу.

2. Використання попередньо скомпільованих смартконтрактів

Попередньо скомпільовані контракти надають складні бібліотечні функції, такі як криптографічні та хешування операцій. Оскільки код не виконується на EVM, а виконується локально на клієнтському вузлі, потрібно менше Gas. Використання попередньо скомпільованих контрактів може заощадити Gas, зменшуючи обсяг обчислювальних робіт, необхідних для виконання смартконтрактів.

Приклади попередньо скомпільованих смартконтрактів включають алгоритм цифрового підпису на основі еліптичних кривих ###ECDSA( та хеш-алгоритм SHA2-256. Використовуючи ці попередньо скомпільовані смартконтракти в смартконтрактах, розробники можуть знизити витрати на Gas та підвищити ефективність роботи застосунків.

) 3. Використання вбудованого асемблерного коду

Вбудована асемблія ### in-line assembly ( дозволяє розробникам писати низькорівневий, але ефективний код, який може безпосередньо виконуватись EVM, без необхідності використання дорогих операційних кодів Solidity. Вбудована асемблія також дозволяє більш точно контролювати використання пам'яті та зберігання, що ще більше зменшує витрати на Gas. Крім того, вбудована асемблія може виконувати деякі складні операції, які важко реалізувати лише за допомогою Solidity, що забезпечує більшу гнучкість для оптимізації споживання Gas.

Однак використання вбудованого асемблера також може нести ризики.

ETH-6.73%
Переглянути оригінал
Ця сторінка може містити контент третіх осіб, який надається виключно в інформаційних цілях (не в якості запевнень/гарантій) і не повинен розглядатися як схвалення його поглядів компанією Gate, а також як фінансова або професійна консультація. Див. Застереження для отримання детальної інформації.
  • Нагородити
  • 3
  • Поділіться
Прокоментувати
0/400
StrawberryIcevip
· 07-31 07:32
Газові витрати дійсно нестерпні
Переглянути оригіналвідповісти на0
OnChainDetectivevip
· 07-31 07:22
Економія на газі - це економія.
Переглянути оригіналвідповісти на0
JustHodlItvip
· 07-31 07:06
цінні інсайти满满太赞了
Переглянути оригіналвідповісти на0
  • Закріпити