Как смоделировать конкуренцию в майнинге между майнерами и дядями?

Я хотел бы действительно понять майнинг pow, реализовав простой, но все еще борющийся.

предположим, что у нас есть пять майнеров, m1,...,m5. У каждого майнера хешрейт, m1=30%, m=20%,m3=15,m4,25, m5=10%, всего 100%

Как смоделировать (например, в простом коде на питоне) соревнование по майнингу между этими майнерами таким образом, чтобы каждые 15 секунд один из них находил новый блок с учетом их хешрейта. например, возможно, что два или три майнера получили блок одновременно. поэтому каждый блок распределяется (скажем, по времени) и подтверждается другими. Как это смоделировать? определить количество устаревших/дядей блоков и т. д.

Может кто поможет и подскажет в этом.

Ответы (1)

Редактировать : я потратил несколько часов на написание кода, который имитирует время распространения блока и дяди. Вы можете найти его в моем репозитории GitHub здесь: https://github.com/lungj/ethtools . Речь идет о программе mine_sim.py. Я подумал, что было бы немного странно публиковать такую ​​длинную программу в StackExchange.

Кроличья нора может быть довольно глубокой, в зависимости от того, насколько глубоко вы хотите моделировать объекты. В реальном мире майнинга майнеры вычисляют хэши определенных значений. Когда хэши удовлетворяют некоторым условиям, хешированные данные могут быть распространены в блокчейне. Когда блокчейн находится в равновесии по сложности и скорости хэширования, а время блока равно b , для каждого временного шага ts в вашей симуляции существует вероятность ( скорость хэширования / общая скорость хеширования ) * b / ts ) того, что блок будет добыт конкретным майнером.

Вот симуляция, которая игнорирует время распространения блока. Можно, конечно, добавить. То, как вы это сделаете, зависит от свойств сети, которую вы хотите смоделировать. Вы можете создать грубый расчет дяди, изменив TIMESTEP на время распространения вашего блока, и всякий раз, когда более одного майнера находят блок на одном и том же временном шаге моделирования, вы можете считать это дядей. Если вам нужна более сложная модель, для каждого узла вы можете сохранить состояние цепочки с точки зрения этого узла (с предположением, что некоторые узлы также являются майнерами). Вы можете моделировать задержки распространения между отдельными узлами, чтобы более реалистично имитировать распространение блоков. Затем вы захотите выбрать реалистичное число разветвлений для каждого узла (или смоделировать формирующиеся и разорванные соединения) и, возможно, смоделировать географическое распределение различных узлов. И, конечно же,

#!/usr/bin/env python3
import random

class Miner(object):
    def __init__(self, name, hashrate):
        '''Initialize a new miner named name with hashrate measured in hashes per second.'''
        self.name = name
        self.hashrate = hashrate

MINERS = [
    Miner('Alice', 30e6),
    Miner('Bob', 20e6),
]

TIMESTEP = 0.01     # Timestep of simulation
BLOCKTIME = 15      # Average number of seconds per block

TOTAL_HASHPOWER = sum([miner.hashrate for miner in MINERS])
time = 0

while True:
    for miner in MINERS:
        if (random.random() * (TOTAL_HASHPOWER / miner.hashrate)) < (TIMESTEP / BLOCKTIME):
            print("t=%0.3f: %s mined a block" % (time, miner.name))
    time += TIMESTEP
Большое спасибо за этот ответ. не могли бы вы уточнить, что вы подразумеваете под отметкой времени здесь и почему она равна 0,01? Кроме того, я не понимаю условие IF в цикле. Я попробовал код, и он отлично работает. Что касается времени распространения блока (задержки), предположим, что после того, как майнер нашел блок, существует задержка со случайным числом в среднем 12 секунд, чтобы блок достиг всех других майнеров. Как тогда вычислять дяди, моделировать их включение и разрешать вилки?. Я был бы признателен, если бы вы могли расширить это (время распространения блока может быть случайным временем и не зависит от местоположения или других сетевых атрибутов).
Временной шаг — это дискретный шаг времени в моделировании (наименьший квант). Это также относится к текущей итерации моделирования. Вы всегда можете улучшить точность модели, пока не проведете эксперимент в реальном мире, так что я оставлю это на ваше усмотрение. И то, что вы выбираете для моделирования, сильно зависит от того, что вы хотите выяснить. И непонятно, что вы моделируете. Статистические модели дают лучшие результаты без длительных симуляций (и не подвержены случайным прогонам). Например, ethereum.stackexchange.com/questions/18201/…
Спасибо. если время распространения блока составляет 12 секунд, должен ли я заменить TIMESTEP как в условии if, так и в последнем выражении, где time += TIMESTEP, изменив 0,01 на 12?
Время распространения блока в этом моделировании не моделируется. Вы можете изменить время блока на 12 секунд, изменив только строку BLOCKTIME = 15.
@MWH Я обновил свой ответ, включив в него ссылку на программу, которую я написал для более глубокого моделирования.
Спасибо. Кажется, в строке 68 для дядей есть ошибка, так как я не мог ее запустить. Выглядит хорошо! но я не мог получить, где хранится информация о блоке. например, chainstate возвращает вознаграждение, полученное каждым майнером. как узнать, сколько блоков было успешно добыто каждым майнером и сколько блоков-дядей произвел каждый майнер? например, если Алиса и Боб сгенерировали блоки в течение короткого промежутка времени (15 секунд), один блок будет подтвержден, а другой будет дядей.
Исправлено (кажется, я нажал кнопку отмены в своем редакторе перед сохранением). Если вы хотите узнать, сколько дядей и блоков у отдельного майнера в каждой цепочке, вы можете увеличить блок кода, начиная со строки 68, и сохранить счетчик дядей (вместо или в дополнение к подсчету вознаграждений за блок). В реальной жизни (и в этой симуляции, если заполнить ее таким же образом) не гарантируется, что Алиса и Боб генерируют блоки одновременно, что приведет к тому, что у кого-то из них будут блоки, которые кто-либо использует в качестве дяди. И, конечно же, форки случаются постоянно, так что у кого что есть, всегда зависит от точки зрения.
Или, если вы хотите определить количество добытых дядей и блоков, вы можете сделать это как обычно: выберите цепочку, для которой вы хотите подсчитать статистику, и пройдитесь по цепочке. Дядюшки каждого блока и майнеры для каждого блока (в том числе неподключенные) хранятся в смоделированных цепочках.