Вот родилась интересная задачка.
Есть список цветов, допустимых в приложении. Известны их RGB-коды. Пользователь, создавая css-файл, который пользует приложение, может ввести любое RGB-значение. Задача: определить цвет, имеющейся в наличии, наиболее похожий на введенный.
Эммм.. И в чём проблема?
Попробуй самое простое и примитивное решение. В зависимости от того, как пользователь задал цвет(в процентах, в 16тиричном или 10ричном формате) перегоняешь его в десятеричный, заносишь в массив из трёх элементов(соответственно) и сравниваешь с тем, что у тебя есть. Тот, у которого разница по всем трём элементам наименьшая - твой искомый.
Если я в чём-то ошибся или недопонял, то пиши, исправим =)
Маленькое уточнение... А на чём прогаешь-то?
RGB - это декартово пространство, стало быть для определения расстояния между точками подходит Декартава метрика. :)
Если говорить просто, то RGB цвет - это координаты точки в пространстве, где по осям будут красная, зелёная и жёлтая составляющая.
Стало быть, чтобы узнать расстояние между цветами, нужно сложить квадраты разностей соответствующих составляющих.
#python
def sqr(a):
returtn a*a
def distance(c1, c2):
return math.sqrt(sqr(c1.r - c2.r) + sqr(c1.g - c2.g) + sqr(c1.b - c2.b))
def find_nearest(colors, cl):
nearest = colors[0]
dist = distance(nearest, cl)
for c in colors:
if distance(c, cl) < dist:
nearest = c
dist = distance(c, cl)
return nearest
Все гениальное просто!
Придется перебрать все цвета (например, если цвет черный). А если их очень много?
Кого много? :)
Можно придумать довольно много алгоритмов оптимизации, только сначала нужно знать как много будет доступных цветов, как они будут распределены в пространстве, как часто понадобится выполнять операцию поиска, как будут распределены входящие цвета... :)
Например, если входящих цветов будет не очень много - то проще всего сделать кеширование - запоминать для каждого пришедшего цвета найденный ближайший и не искать его заново. :)
Если доступные цвета равномерно распределены в пространстве RGB может хорошо подойти метод загрубления координат.
Если всего много, может подойти R-дерево.
Но в любом случае, я сильно советую сначала реализовать самый простейший алгоритм безо всяческих оптимизаций.
А вот если наткнёшся в этом месте на тормоза - можно и оптимизировать для имеющихся данных. :)
Разве что взятие квадратного корня можно убрать - на результат оно не влияет. :)
Отправить комментарий