Bu bir grafik renklendirme problemidir .
Bir grafik boyamanın, bir kenarı paylaşan iki köşe de aynı renge sahip olmayacak şekilde bir grafiğin köşelerine bir renk ataması olduğunu hatırlayın. Özellikle, grafiğin (soyut) köşeleri çokgenlerdir. Kesiştiği zaman (çokgenler olarak) iki köşe (yönlendirilmemiş) kenara bağlanır. Çokgenlerin ( k ) ayrık koleksiyonlarının bir dizisi olan soruna herhangi bir çözüm alırsak ve dizideki her koleksiyona benzersiz bir renk atarsak, grafiğin k- rengini elde etmiş oluruz . Küçük bir k bulmak istenir .
Bu sorun oldukça zor ve keyfi grafikler için çözülmemiş durumda. Kodlaması kolay olan yaklaşık bir çözümü düşünün. Sıralı bir algoritma yapmalıdır. Welsh-Powell algoritması, köşelerin dereceye göre azalan düzenine dayanan açgözlü bir çözümdür. Orijinal çokgenlerin diline çevrilen, önce çokgenleri üst üste geldikleri diğer çokgenlerin sayısına göre azalan sırada sıralayın. Sırayla çalışarak, ilk çokgene başlangıç rengi verin. Birbirini izleyen her adımda, bir sonraki çokgeni mevcut bir renkle renklendirmeyi deneyin: yani, olmayan bir renk seçinbu çokgenin komşuları tarafından zaten kullanılıyor. (Kullanılabilir renkler arasında seçim yapmanın birçok yolu vardır; en az kullanılanı deneyin veya rastgele birini seçin.) Bir sonraki çokgen mevcut bir renkle renklendirilemiyorsa, yeni bir renk oluşturun ve bununla renklendirin.
Az sayıda renkle bir renklendirme elde ettikten sonra, zonalstatları renge göre renklendirin: inşaat ile, belirli bir rengin iki çokgeninin örtüşmemesi garanti edilir.
İşte içinde örnek kod R
. (Python kodu çok farklı olmaz.) İlk olarak, gösterilen yedi çokgen arasında örtüşmeleri açıklıyoruz.
edges <- matrix(c(1,2, 2,3, 3,4, 4,5, 5,1, 2,6, 4,6, 4,7, 5,7, 1,7), ncol=2, byrow=TRUE)
Yani, 1 ve 2 poligonları üst üste bindirilir ve 2 ve 3, 3 ve 4, ..., 1 ve 7 poligonları da üst üste gelir.
Köşeleri azalan dereceye göre sıralayın:
vertices <- unique(as.vector(edges))
neighbors <- function(i) union(edges[edges[, 1]==i,2], edges[edges[, 2]==i,1])
nbrhoods <- sapply(vertices, neighbors)
degrees <- sapply(nbrhoods, length)
v <- vertices[rev(order(degrees))]
(Ham) ardışık renklendirme algoritması, üst üste binen herhangi bir çokgen tarafından kullanılmayan en eski rengi kullanır:
color <- function(i) {
n <- neighbors(i)
candidate <- min(setdiff(1:color.next, colors[n]))
if (candidate==color.next) color.next <<- color.next+1
colors[i] <<- candidate
}
Veri yapılarını ( colors
ve color.next
) başlatın ve algoritmayı uygulayın:
colors <- rep(0, length(vertices))
color.next <- 1
temp <- sapply(v, color)
Çokgenleri renge göre gruplara ayırın:
split(vertices, colors)
Bu örnekteki çıktı dört renk kullanır:
$`1`
[1] 2 4
$`2`
[1] 3 6 7
$`3`
[1] 5
$`4`
[1] 1
Çokgenleri örtüşmeyen dört gruba ayırmıştır. Bu durumda çözüm optimal değildir ({{3,6,5}, {2,4}, {1,7}} bu grafik için üç renklidir). Genel olarak aldığı çözüm çok kötü olmamalıdır.