Задания
Версия для печати и копирования в MS Word
Тип 27 № 76242
i

Учёный решил про­ве­сти кла­сте­ри­за­цию не­ко­то­ро­го мно­же­ства звёзд по их рас­по­ло­же­нию на карте звёзд­но­го неба. Кла­стер звёзд  — это набор звёзд (точек) на гра­фи­ке. Каж­дая звез­да обя­за­тель­но при­над­ле­жит толь­ко од­но­му из кла­сте­ров. Центр кла­сте­ра, или цен­т­ро­ид,  — это одна из звёзд на гра­фи­ке, сумма рас­сто­я­ний от ко­то­рой до всех осталь­ных звёзд кла­сте­ра ми­ни­маль­на. Рас­сто­я­ние между двумя точ­ка­ми  A левая круг­лая скоб­ка x_1, y_1 пра­вая круг­лая скоб­ка и  B левая круг­лая скоб­ка x_2, y_2 пра­вая круг­лая скоб­ка вы­чис­ля­ет­ся по фор­му­ле:  d левая круг­лая скоб­ка A, B пра­вая круг­лая скоб­ка = ко­рень из: на­ча­ло ар­гу­мен­та: левая круг­лая скоб­ка x_1 минус x_2 пра­вая круг­лая скоб­ка в квад­ра­те плюс левая круг­лая скоб­ка y_1 минус y_2 пра­вая круг­лая скоб­ка в квад­ра­те конец ар­гу­мен­та .

Даны два вход­ных файла (файл 27A и файл 27Б). В файле 27A хра­нят­ся дан­ные о звёздах двух кла­сте­ров. В каж­дой стро­ке за­пи­са­на ин­фор­ма­ция о рас­по­ло­же­нии на карте одной звез­ды: ко­ор­ди­на­та x, затем ко­ор­ди­на­та y (в услов­ных еди­ни­цах). Из­вест­но, что ко­ли­че­ство звёзд не пре­вы­ша­ет 1000. В файле 27Б хра­нят­ся дан­ные о звёздах трёх кла­сте­ров.

Файл 27А.txt

Файл 27Б.txt

Из­вест­но, что ко­ли­че­ство звёзд не пре­вы­ша­ет 10 000. Струк­ту­ра хра­не­ния ин­фор­ма­ции о звез­дах в файле 27Б ана­ло­гич­на файлу 27А. Воз­мож­ные дан­ные од­но­го из фай­лов ил­лю­стри­ро­ва­ны гра­фи­ком.

Для каж­до­го файла опре­де­ли­те ко­ор­ди­на­ты цен­тра каж­до­го кла­сте­ра, затем вы­чис­ли­те два числа: Px  — сред­нее ариф­ме­ти­че­ское абс­цисс цен­тров кла­сте­ров, и Py  — сред­нее ариф­ме­ти­че­ское ор­ди­нат цен­тров кла­сте­ров. В от­ве­те за­пи­ши­те че­ты­ре числа: в пер­вой стро­ке сна­ча­ла целую часть про­из­ве­де­ния Px × 10 000, затем целую часть про­из­ве­де­ния Py × 10 000 для файла 27А, во вто­рой стро­ке  — ана­ло­гич­ные дан­ные для файла 27Б.

 

Ответ:

Спрятать решение

Ре­ше­ние.

##

from math import dist

data = []

# Для А/Б

for s in open('27Б.txt'):

x, y = [float(d) for d in s.replace(',', '.').split()]

data.append([x, y])

rast = 0.1

clusters = []

while data:

cl = [data.pop()]

for p in cl:

sosed = [p1 for p1 in data if dist(p, p1) < rast]

for p1 in sosed:

cl.append(p1)

data.remove(p1)

clusters.append(cl)

#print(*[len(cl) for cl in clusters]) # - про­ве­ря­ет кол-во кла­сте­ров

# 2 кла­сте­ра для файла A и 3 для файла B

# В слу­чае про­ти­во­ре­чия ме­ня­ем rast - это зна­че­ние (Для A - rast = 1, для B - rast = 0.1)

def centroid(cl):

m = []

for p in cl:

s = 0

for p1 in cl:

s += dist(p, p1)

m.append([s, p])

return min(m)[1]

cen = [centroid(cl) for cl in clusters]

px = sum(x for x, y in cen)/len(cen)

py = sum(y for x, y in cen)/len(cen)

print(int(px*10000), int(py*10000))

 

 

Ответ для A: 51318 7467.

Ответ для B: 62068 6005.

 

При­ведём ре­ше­ние Сер­гея Донец на языке PascalABC.NET.

uses coords;

// Функ­ция опре­де­ле­ния кла­сте­ра для файла 27А

function numClA(p: point):=

(p.x in 3.5..6.0) and (p.y in 1.0..4.0) ? 0 :

(p.x in 4.0..7.0) and (p.y in -2.5..0.5) ? 1 : 2;

// Функ­ция опре­де­ле­ния кла­сте­ра для файла 27Б

function numClB(p: point):=

(p.x in 3.2..6.0) and (p.y in 1.7..4.6) ? 0 :

(p.x in 3.9..6.3) and (p.y in -1.4..1.5) ? 1 :

(p.x in 7.4..10.4) and (p.y in -2.7..-0.1) ? 2 : 3;

function ProcessFile(fname: string; clusters: integer; clFunc: function(p: point): integer): (integer, integer);

begin

var points := ReadAllText(fname).ToReals(',').Batch(2, \(x,y)->Pnt(x,y)).ToArray;

DrawPoints(points);//по ви­зу­а­ли­за­ции пишем гра­ни­цы для numClA(зе­ле­ные точки), numClB(синие точки)

var centers := ArrGen(clusters, c -> begin

var cl := points.Where(p -> clFunc(p) = c).ToArray;

Result := cl.Length = 0? Pnt(0, 0) : cl.MinBy(p -> cl.Sum(q -> Distance(p, q)));

//Result := cl.MinBy(p -> cl.Sum(q -> Distance(p, q)));

end);

Result := (Trunc(centers.Average(p -> p.x) * 10000),

Trunc(centers.Average(p -> p.y) * 10000));

end;

begin

var (aX, aY) := ProcessFile('27А.txt', 2, numClA);

var (bX, bY) := ProcessFile('27Б.txt', 3, numClB);

Println('Ответ для A: ', aX, ' ', aY);

Println('Ответ для B: ', bX, ' ', bY);

end.

 

Источник: Проб­ный ЕГЭ Санкт-Пе­тер­бург, 20.02.2025. Ва­ри­ант 2