Подтвердить что ты не робот

Исправлять ошибки в библиотечном коде или их замечать?

Предположим, у меня есть функция в библиотеке кода с ошибкой, я нашел ошибку в библиотеке кода:

class Physics
{
    public static Float CalculateDistance(float initialDistance, float initialSpeed, float acceleration, float time)
    {
        //d = d0 + v0t + 1/2*at^2
        return initialDistance + (initialSpeed*time)+ (acceleration*Power(time, 2));
    }
}

Примечание. Пример и язык являются гипотетическими.

Я не могу гарантировать, что исправление этого кода не сломает кого-либо.

Вполне возможно, что есть люди, которые зависят от ошибки в этом коде, и что ее исправление может привести к ошибке (я не могу придумать практического пути, который может произойти; возможно, это как-то связано с созданием поиска). таблица расстояний, или, может быть, они просто выдают исключение, если расстояние является неправильным значением, а не тем, что они ожидают)

Должен ли я создать 2-ю функцию:

class Physics
{
    public static Float CalculateDistance2(float initialDistance, float initialSpeed, float acceleration, float time) { ... }

    //Deprecated - do not use. Use CalculateDistance2
    public static Float CalculateDistance(float initialDistance, float initialSpeed, float acceleration, float time) { ... }
}

На языке без способа формального устаревания кода, я просто доверяю всем переключиться на CalculateDistance2?

Это также отстойно, потому что теперь идеально названная функция (CalculateDistance) навсегда потеряна для унаследованной функции, которая, вероятно, никому не нужна и не хочет ее использовать.

Должен ли я исправить ошибки или отказаться от них?

Смотрите также

4b9b3361

Ответ 1

Вам никогда не удастся удовлетворить все существующие проекты, используя вашу библиотеку. Попытка сделать это может создать приветливое чувство предсказуемости, но это также приведет к раздуванию и застою. В конце концов, это оставит его подверженным замене гораздо более сжатой библиотекой.

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

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

Итак, я бы честно сказал, чтобы исправить это.

Ответ 2

Я несколько раз сражался в течение нескольких дней с некоторым кодом MFC, который вел себя совершенно неожиданным образом. Когда я наконец выяснил, что это была ошибка в поставляемой Microsoft библиотеке, я проверил базу знаний. Он был задокументирован как (примерно) "это известная ошибка, которую мы нашли 2 версии ОС назад. Мы не исправляем ее, потому что кто-то, вероятно, зависит от нее".

Я был немного сумасшедшим...

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

Ответ 3

Хороший вопрос. Я с нетерпением жду некоторых других ответов. Вот мои 2 цента по проблеме:

Как правило, если вы подозреваете, что многие люди действительно полагаются на ошибку, то это аргумент для того, чтобы не исправлять ошибку и вместо этого создавать новую функцию CalculateDistance2.

С другой стороны, и я думаю, что лучший вариант, не забывайте, что люди, которые полагаются на ошибку, всегда могут использовать определенную, более старую версию вашей библиотеки. Вы можете документировать удаление ошибки (и, следовательно, измененного поведения или функции библиотеки) в примечаниях к выпуску.

(Если ваш класс является COM-компонентом, обычной мудростью будет создание нового интерфейса ICalculateDistance2, который делает оригинальный интерфейс устаревшим, но сохраняет его для обратной совместимости.)

Ответ 4

Другой вариант - исправить ошибку, но оставить старый код в виде метода LegacyCalculateDistance, который доступен, если кому-то это действительно нужно.

Вы даже можете реализовать возможность выбора "устаревшей" реализации на основе (например) файла конфигурации или настройки переменной среды, если вы заинтересованы в том, чтобы предлагать решение совместимости для пользователей, которые, возможно, не смогут сделать изменения на уровне кода.

Ответ 5

Как вы описали, это компромисс между удовлетворением двух разных групп пользователей:

  • Существующие пользователи, которые создали свое программное обеспечение на основе ошибки в вашей библиотеке
  • Новые пользователи, которые будут использовать вашу библиотеку в будущем

Нет идеального решения, и я не думаю, что есть универсальный ответ. Я думаю, что это полностью зависит от ошибки и функции.

Я думаю, вы должны спросить себя

"Функционирует ли функция с существующей ошибкой?"

Если это так, то оставьте это в библиотеке. В противном случае я, вероятно, выброшу его.

Ответ 6

Просто ради аргумента, предположим, что ваш гипотетический язык был С++ (хотя он намного больше похож на Java). В этом случае я бы использовал пространства имен для создания вилки, с которой (разумно) было легко справиться с точки зрения как нового, так и устаревшего кода:

namespace legacy {
class physics { 
    Float CalculateDistance(float initialDistance, float initialSpeed, float acceleration, float time)
    {
    // original code here
    } 
}
}

namespace current { 
class physics {
    Float CalculateDistance(float initialDistance, float initialSpeed, float acceleration, float time)
    {
    // corrected code here
    } 
}

Оттуда у вас есть несколько вариантов выбора между ними. Например, существующий код может добавить директиву using: using legacy::physics;, и они будут продолжать использовать существующий код без каких-либо дополнительных изменений. Новый код мог бы добавить using current::physics; вместо этого, чтобы получить текущий код. Когда вы это сделаете, вы (вероятно) осудите класс legacy::physics и заплатите его для удаления через определенный период времени, количество ревизий или что-то еще. Это дает вашим клиентам возможность проверить свой код и переключиться на новый код упорядоченным образом, сохраняя при этом пространство имен legacy слишком загрязненным старым нежелательным файлом.

Если вы действительно хотите получить подробную информацию об этом, вы даже можете добавить схему нумерации версий в свои пространства имен, поэтому вместо legacy::physics она может быть v2_7::physics. Это позволяет предположить, что даже когда вы "исправляете" код, возможно, возможно, что все еще может быть ошибка или две слева, поэтому вы можете закончить ее повторное редактирование, а кто-то может оказаться в зависимости от какой-либо произвольной версии, не обязательно только оригинальный или текущий.

В то же время это ограничивает "осведомленность" версии, которая будет использоваться для одной (довольно) небольшой части кода (или, по крайней мере, небольшой части каждого модуля) вместо того, чтобы распространяться по всему коду. Он также дает довольно безболезненный способ компиляции модуля с использованием нового кода, проверки ошибок, возврата к старым кодам, если это необходимо, и т.д., Без необходимости иметь дело непосредственно с каждым отдельным вызовом рассматриваемой функции.