Проблема:
Учитывая непустое множество точек в декартовой плоскости, найдите наименьший круг, который охватывает их все ( ссылка на Википедию ).
Эта проблема тривиальна, если число точек равно трем или меньше (если есть одна точка, радиус окружности равен нулю; если имеется две точки, то отрезок линии, соединяющий точки, является диаметром круга; если есть В трех (не коллинеарных) точках можно получить уравнение окружности, которая касается их всех, если они образуют не тупой треугольник, или окружность, которая касается только двух точек и окружает третью, если треугольник тупой). Итак, ради этого испытания количество очков должно быть больше трех.
Соревнование:
- Ввод: список из 4 или более неколинейных точек. Точки должны иметь координаты X и Y; координаты могут быть плавающими. Чтобы облегчить задачу, никакие две точки не должны иметь одинаковую координату X.
Например:[(0,0), (2,1), (5,3), (-1,-1)]
- Вывод: кортеж значений,
(h,k,r)
такой что - это уравнение наименьшего круга, охватывающего все точки.
Правила:
- Вы можете выбрать любой метод ввода, подходящий для вашей программы.
- Вывод должен быть напечатан
STDOUT
или возвращен функцией. - «Обычные» языки общего назначения предпочтительны, но приемлем любой язык.
- Можно предположить, что точки не являются коллинеарными.
- Это код-гольф, поэтому выигрывает самая маленькая программа в байтах. Победитель будет выбран через неделю после объявления конкурса.
- Пожалуйста, укажите язык, который вы использовали, и длину в байтах в качестве заголовка в первой строке вашего ответа:
# Language: n bytes
- Пожалуйста, укажите язык, который вы использовали, и длину в байтах в качестве заголовка в первой строке вашего ответа:
Тестовые случаи:
- 1:
- Входные данные:
[(-8,0), (3,1), (-6.2,-8), (3,9.5)]
- Выход:
[-1.6, 0.75, 9.89]
- Входные данные:
- 2:
- Входные данные:
[(7.1,-6.9), (-7,-9), (5,10), (-9.5,-8)]
- Выход:
[-1.73, 0.58, 11.58]
- Входные данные:
- 3:
- Входные данные:
[(0,0), (1,2), (3,-4), (4,-5), (10,-10)]
- Выход:
[5.5, -4, 7.5]
- Входные данные:
- 4:
- Входные данные:
[(6,6), (-6,7), (-7,-6), (6,-8)]
- Выход:
[0, -0.5, 9.60]
- Входные данные:
Удачного игры в гольф !!!
Ответы:
Wolfram Language (Mathematica) ,
2827 байтовПопробуйте онлайн!
Встроенные модули здесь удобны. Выход - это дисковый объект с центром и радиусом. Как и другие, я обнаружил, что 2-й и 3-й тестовые случаи отличаются от вопроса.
Спасибо @lirtosiast за сохранение байта!
Если список требуется в качестве выходных данных, это может быть сделано в 35 байтах (за счет дополнительных 8 байтов) . Спасибо @Roman за указание на это.
источник
Append@@BoundingRegion[#,"MinDisk"]&
JavaScript (ES6),
298 ... 243242 байтаВозвращает массив
[x, y, r]
.Попробуйте онлайн!
или посмотрите отформатированную версию
Как?
метод
Для каждой пары точек(A,B) , мы создаем круг (X,Y,r) , диаметр которого Б .AB
Для каждой тройки различных точек(A,B,C) , мы создаем круг (X,Y,r) , который огибает треугольник B C .ABC
For each generated circle, we test whether each point(x,y) is enclosed within it:
And we eventually return the smallest valid circle.
Implementation
In the JS code, the formula to compute(X,Y) for the triangle's circumscribed circle is slightly simplified. Assuming d≠0 , we define q=Cx2+Cy2 , leading to:
This way, the helper functionF requires only two parameters (j,k) to compute each coordinate:
The third parameter used inF (i.e. its actual argument s ) is used to compute (X,Y) when d=0 , meaning that the triangle is degenerate and we have to try to use the diameter instead.
источник
R, 59 bytes
Try it online!
Takes input as a vector of complex coordinates.
Mod
is the distance (modulus) in the complex plane andnlm
is an optimization function: it finds the position of the center (output asestimate
) which minimizes the maximum distance to the input points, and gives the corresponding distance (output asminimum
), i.e. the radius. Accurate to 3-6 digits; the TIO footer rounds the output to 2 digits.nlm
takes a numeric vector as input: they%*%c(1,1i)
business converts it to a complex.источник
Jelly,
10098 bytesTry it online!
In contrast to my Wolfram language answer, Jelly needs quite a lot of code to achieve this (unless I’m missing something!). This full program takes the list of points as its argument and returns the centre and radius of the smallest enclosing circle. It generates circumcircles for all sets of three points, and diameters for all sets of two points, checks which include all of the points and then picks the one with the smallest radius.
Code for the make_circumcircle bit was inspired by code at this site, in turn inspired by Wikipedia.
источник
APL(NARS), 348 chars, 696 bytes
This is one 'implementation' of formulas in Arnauld solution...Results and comments:
f: finds the combination of alpha ojets in the omega set
((X,Y), r) from now represent one circonference of radius r and center in (X Y).
c: finds if the point in ⍺ is inside the circumference ((X Y) r) in ⍵ (result <=0) ot it is external (result >0) In the case of circumference input in ⍵ it is ⍬ as input, it would return 1 (out of circumference) each possible input in ⍺.
p: if ⍵ is an array of ((X Y) r); for each of the ((X Y) r) in ⍵ writes 1 if all points in the array ⍺ are internal to ((X Y) r) otherwise writes 0 NB Here's something that do not goes because I had to round to epsilon= 1e¯13. in other words in limit cases of points in the plane (and probably built on purpose) it is not 100% solution insured
s2: from 2-point in ⍵, it returns the circumference in the format ((X Y) r) that has diameter in those 2 points
s3: from 3 points it return the circumference in the format ((X Y) r) passing through those three points If there are problems (for example points are aligned), it would fail and return ⍬.
note that -.× find the determinant of a matrix nxn and
s: from n points in ⍵, it finds the type circumferences of those found by s2 or those of type s3 that contain all n points.
s1: from the set found from the s above calculates those that have minimum radius and returns the first one that has minimal radius. The three numbers as arrays (the first and second coordinates are the coordinates of the center, while the third is the radius of the circumference found).
источник
Python 2 (PyPy),
244242 bytesTry it online!
This uses the brute-force O(n^4) algorithm, iterating through each pair and triangle of points, calculating the centre, and keeping the centre that needs the smallest radius to enclose all points. It calculates the circumcentre of 3 points via finding the intersection of two perpendicular bisectors (or, if two points are equal it uses the midpoint with the third).
источник
P={x+y*1j for x,y in input()}
saves 2 bytes as well.Python
212190 bytesThis solution is incorrect, and I have to work now so I do not have time to fix it.
Try it online!
I figured out which two points are furthest and then I generated an equation for a circle based off those points!
I know this isn't the shortest in python, but it's the best I could do! Also this is my first attempt at doing one of these, so please be understanding!
источник
if g>c:\n c=g\n d=[e,f]
toif g>c:c=g;d=[e,f]
, saving you a lot of whitespace. I don't think you need to initialise d beforehand, also using two variables andE,F=e,f
in line 10 will make yourprint
a lot shorter. I think a solution withmax
and a list comprehension would be even shorter than two loops, but I might be wrong. Sadly, however, your solution is not correct. For the points (-1,0), (0,1.41), (0.5, 0), (1,0) your solution computes a circle around 0 with radius 1. But the point (1, 1.41) is not in that circle.