Почему когда я нажимаю кнопку «запустить» в python, это не дает никакого выхода? - PullRequest
0 голосов
/ 13 января 2020

Я начал курс python несколько дней go. У меня проблемы с моим l oop в назначении python, которое:

Учитывая набор из N измерений, (r1, r2, ..., rN), мы первоначально назначим нечетное измерения с номером 1 для класса и измерения с четным номером для класса 2. Затем повторяются следующие два шага:

• Шаг обновления: вычисление среднего значения (среднего) измерений в каждом кластере.

• Шаг назначения: назначьте каждое измерение кластеру с ближайшим средним значением. В случае ie назначьте измерение для кластера 1.

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

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

Я создал код:

import numpy as np
import math
def clusterAnalysis(reflectance):
    ref=np.size(reflectance)# all N measurements
    even=np.any(ref %2==0)# N measurements are even numbers
    uneven=np.any(ref%2>0)# N measurements are odd number
    mean1=np.mean(even)#average of even numbers in cluster 2
    mean2=np.mean(uneven)# average of odd numbers in cluster 1
    sub1=abs(ref-mean1)
    sub2=abs(ref-mean2)
    while sub1<=sub2:
        clusterAssigment="1"
    else:
        clusterAssigment="2"
    return clusterAssigments
#print(clusterAnalysis(np.array([1.7, 1.6, 1.3, 1.3, 2.8, 1.4,
#2.8, 2.6, 1.6, 2.7])))

** Новый код:

import math
def clusterAnalysis(reflectance):
    reflectance=np.arange(reflectance.size)
    evens =reflectance % 2 == 0 # N measurements are even numbers
    clusters = np.ones(reflectance.shape)
    clusters[evens] = 2
    while True:
        mean_even=np.mean(reflectance[evens])
        mean_odd=np.mean(reflectance[np.logical_not(evens)])
        diff_even = np.abs(reflectance - mean_even) 
        diff_odd = np.abs(reflectance - mean_odd)
        new_clusters= np.ones(reflectance.shape)
        new_clusters[diff_even < diff_odd] = 2
        clusterAssigments= new_clusters

        if np.all(clusters == new_clusters):
            break
        clusters = new_clusters
        clusterAssigments= new_clusters
    return clusterAssigments 
print(clusterAnalysis(np.array([1.7, 1.6, 1.3, 1.3, 2.8, 1.4,2.8, 2.6, 1.6, 2.7])))```**



The code above does not work at all. My output should be :`2 2 2 2 1 2 1 1 2 1 `
I have been working on this for last 2 days and I just dont know what I am doing wrong...

1 Ответ

1 голос
/ 13 января 2020

Ваше время l oop никогда не заканчивается. Вы никогда не изменяете sub1 или sub2, поэтому l oop просто вращается и вращается, а sub1 всегда меньше sub2.

Проблема, с которой вы сталкиваетесь, заключается в том, что на каждом итерации, пока l oop, вы работаете с новыми кластерами на основе среднего значения от старых кластеров, а затем проверяете, изменились ли они.

Вы правы, что вам нужно какое-то время l oop, вы можете использовать что-то вроде этого:

def clusterAnalysis(reflectance):
    # Work out your odd/even clusters to start it off
    # EDIT: I misread how this bit works - see the update.
    # You don't want to use the size here:
    #     you want to use a list of numbers the size
    # of reflectance [0, 1, 2, ..., n]
    even_numbers = np.arange(reflectance.size) % 2 == 0

    # Now we'll create an array to hold the cluster ids, that's the
    # same shape as reflectance.
    # By default it'll store ones. Then we'll change all the entries
    # for even numbers to hold twos
    clusters = np.ones(reflectance.shape)

    # This uses what's called "logical indexing" - it'll change all the elements
    # that equal "true" in even_numbers
    clusters[even_numbers] = 2

    # This will create a never-ending while loop, but we'll manually
    # end it using 'break'
    while True:
        # Work out the new clusters, by working out the means of the two 
        # clusters and finding the closest to the reflectance numbers
        # Clue: You can use logical indexing here like we did above
        cluster_1_mean = ...
        cluster_2_mean = ...
        new_clusters = ...

        # This is the really important bit - we've created the new array 
        # `new_clusters` above and we want to check if it's the same as 
        # the last one. If it is, we'll use `break` which tells python
        # to stop doing the loop now.
        if np.all(clusters == new_clusters):
            break

        # We'll only reach here if we haven't called 'break' - so we'll update with the new clusters and we can go again
        clusters = new_clusters

    # Once the while loop is finished, we should return the clusters array.
    return clusters

РЕДАКТИРОВАТЬ: Я постараюсь дать вам кусочки головоломки для бит кластеризации.

Допустим, у меня есть два списка из 20 случайных чисел от 0 до 200, и я хочу получить среднее значение нечетных и четных значений:

x = np.random.randint(200, size=(20))

# Just like above, we'll get the id of each element in an array [0, 1, ..., 20]
x_ids = np.arange(x.size)
evens = x_ids % 2 == 0

# We'll get the mean of all the even `x`'s
mean_even = np.mean(x[evens])

# And we can do it the other way round for the odds
mean_odd = np.mean(x[np.logical_not(evens)])

Другое редактирование:

ОК, последний кусок головоломки:)

Итак, мы хотим найти, какой из x ближе всего к mean_even, а какой ближе к mean_odd. Мы можем сделать что-то похожее на вашу первоначальную попытку:

diff_even = np.abs(x - mean_even) 
diff_odd = np.abs(x - mean_odd)

# Start by creating a new clusters array, just like we did before,
# where all the ids are originally set to `1`.    
new_clusters = np.ones(x.shape)

# Now get the numbers closest to `diff_even` and set their cluster to
# two.
# Because we're using less-than, it means that any that are equally
# close to both means will stay in cluster one. If we wanted it to
#  work so they went to cluster 2 by default, we could use `<=`.
new_clusters[diff_even < diff_odd] = 2

Вам нужно будет изменить некоторые имена переменных, чтобы использовать логическое индексирование, чтобы получить средства из массива кластеров вместо массива четных, но это должно дать вам в основном все, что вам нужно.

Обратите внимание, что я сделал ошибку раньше, когда сделал mean_odd. Я нарушил логическое индексирование, случайно превратив логический массив в числа, поэтому я обновил его для использования np.logical_not. Я могу объяснить, как это работает более подробно, если это интересно.

...