Los neoyorquinos de Politico eligen un nuevo alcalde después de que comienzan las caóticas e históricas primarias:
NUEVA YORK — Las urnas cerraron en la primera elección por orden de preferencia en la historia de la ciudad de Nueva York y, aunque la suerte está echada, es posible que los votantes no sepan el resultado durante semanas.
[...] Ampliar aún más el conteo de boletas es el advenimiento de la votación por orden de preferencia, que permite a los neoyorquinos seleccionar hasta cinco candidatos para cada puesto. El sistema se activa cuando ningún candidato obtiene el 50 por ciento de los votos en el primer pase. La junta planea emitir los resultados preliminares de las votaciones clasificadas el 29 de junio.
De acuerdo con esto :
Más de una docena de demócratas y dos republicanos competirán para reemplazar al alcalde saliente Bill de Blasio (D). Se espera que la elección por orden de preferencia tarde semanas en resolverse.
Por lo tanto, la cantidad de formas distintas pero válidas en las que una persona puede votar es grande. Creo que es la suma de 0, 1, 2, 3, 4 y 5 de 14 posibilidades, pero ni siquiera estoy seguro de eso (ver más abajo).
Tengo curiosidad por saber cómo la ciudad de Nueva York implementará física y computacionalmente el conteo de votos por orden de preferencia.
Pregunta: Algorítmicamente , se puede hacer a través de varias pasadas de una función de clasificación sobre todos los votos de elección por orden de preferencia en una tabla en la memoria o en un disco duro, pero ¿cómo implementan esto con las diversas formas físicas de los votos emitidos en las elecciones para la alcaldía de Nueva York? ?
¿Recurrirán a toda la implementación electrónica del algoritmo, todo físico, o algún método híbrido?
En Python, asumiendo (por ejemplo) exactamente 14 candidatos disponibles (en matemáticas es el número de permutaciones sin repeticiones )
from itertools import permutations
possible = []
for k in [0, 1, 2, 3, 4, 5]:
uniques = list(permutations('abcdefghijklmn', k))
possible.append(uniques)
print(k, len(uniques))
all_possible = sum(possible, [])
print('total: ', len(all_possible))
k uniques
0 1
1 14
2 182
3 2184
4 24024
5 240240
total: 266645
Creo que el conteo se puede hacer a mano (usando varios 'pasos' si es necesario). Por ejemplo, en Canadá, según CBC.ca (sobre la votación clasificada en Canadá):
"Son realmente simples. Son tan fáciles como uno, dos, tres. Clasificas tus opciones en orden, entonces, ¿quién quiero que sea alcalde, quién es mi primera opción, quién es mi segunda opción y quién es mi tercera opción?
En la primera ronda, solo sumamos las primeras opciones, y si alguien tiene la mayoría, se acabó. Ellos ganan. Pero si nadie tiene la mayoría, digamos que la persona con más votos solo tiene el 30 por ciento, entonces obviamente no debería ser el alcalde necesariamente.
Así que elimina al candidato con la menor cantidad de votos y simplemente transfiere esos votos a la segunda opción en cada voto hasta que alguien tenga la mayoría.
Contar esto a mano no parece tan difícil, no necesitaría tener en cuenta todas las posibles combinaciones de boletas en el proceso de conteo.
Como dice la cita, comienza dividiendo las papeletas por primera opción. Si tiene 14 candidatos, entonces tiene 14 montones de boletas. Si no hay un ganador basado en las primeras opciones, entonces elimina al candidato con la menor cantidad de votos (primera opción) y comienza a buscar la segunda opción en las boletas de esa pila. Entonces solo te quedan 13 candidatos en la carrera. este proceso continúa hasta que tenga un ganador.
Así es también como NPR describe el proceso de conteo para la elección de alcalde de la ciudad de Nueva York:
Si alguien obtiene el 50% más uno después de contar todos los votos de primera opción, entonces la elección ha terminado y ese candidato gana.
Pero si nadie obtiene el 50% más uno, se pasa a la Ronda 2.
La persona con el menor número de votos de primer lugar es eliminada y las segundas opciones de los votantes de ese candidato se redistribuyen como votos para otros candidatos.
Esta reasignación de votos continúa hasta que alguien alcanza el 50% más uno.
Sin embargo, en las elecciones de Nueva York, los votos serán contados por una máquina. Como informó CBS News el 25 de mayo de 2021:
Los neoyorquinos pueden esperar saber quién ganó las próximas primarias demócratas para alcalde de la ciudad más rápido de lo que lo hubieran hecho si la Junta Electoral del Estado de Nueva York no hubiera actuado el martes para aprobar el software para tabular los resultados de la votación por orden de preferencia. La decisión significa que la ciudad ahora evitará un largo conteo manual de los votos emitidos en la carrera el próximo mes.
Sin embargo, los resultados probablemente no estarán disponibles de inmediato, del mismo artículo de CBS News :
A pesar de la aprobación del software, aún pasarán días, si no semanas, antes de que los neoyorquinos sepan quién ganó las primarias del 22 de junio. Se espera que los resultados no oficiales de los votos de primera opción se publiquen la noche de las primarias para mostrar los votos de primera opción, pero la Junta Electoral de la ciudad dice que los funcionarios no podrán comenzar a calcular los resultados hasta al menos la semana siguiente.
En cuanto a la implementación específica, ya se ha tratado en profundidad en la respuesta de Zach Lipton .
La ciudad de Nueva York tabuló a mano algunas boletas de elección clasificadas en elecciones especiales a principios de este año, donde la cantidad de boletas y candidatos fue comparativamente pequeña y el conteo manual fue más factible.
Sin embargo, para la elección de alcalde, la Junta Estatal de Elecciones certificó el software para el proceso de conteo: The RCV Universal Tabulator , un paquete de código abierto producido por un grupo sin fines de lucro llamado The Ranked Choice Resource Center.
El software es de código abierto y se puede ver en GitHub . Imagino que las papeletas físicas se escanearán utilizando un equipo típico de tabulación de votos certificado para producir la entrada para el software RCV. Si puede leer Java, el ciclo de tabulación central parece bastante sencillo (el software admite múltiples ganadores, aunque claramente no se usa en esta elección):
// At each iteration, we'll either a) identify one or more
// winners and transfer their votes to the remaining candidates (if we still need to find more
// winners), or b) eliminate one or more candidates and gradually transfer votes to the
// remaining candidates.
Eventualmente, también publicarán el registro completo de votos emitidos, lo que permitirá a cualquiera realizar su propia versión del algoritmo si lo desea.
Creo que está malinterpretando cómo funciona la votación por orden de preferencia. Si, como fue el caso, ningún candidato supera el 50% de los votos, el candidato del último lugar queda eliminado. Sus boletas ahora están todas asignadas a los candidatos de segunda elección de sus votantes. Entonces, los únicos votos que deben volver a contarse son los del candidato del último lugar.
Luego volvemos al principio y simulamos que esos votos recategorizados tienen al candidato de segunda opción como candidato de primera opción, a la tercera opción como segunda opción, etc. y nuevamente observamos si alguien ha cruzado el 50%. Si no, repetimos el proceso con el nuevo candidato del último lugar. Tenga en cuenta que es posible que el umbral del 50 % baje a medida que continúa el proceso si nadie elige un segundo o tercer candidato, etc.
El proceso se describe aquí: https://vote.nyc/page/ranked-choice-voting
También agregaría que (a) no comenzarán el proceso hasta la próxima semana y (2) algunas de las reasignaciones de la primera ronda serán muy rápidas, ya que hay números muy pequeños para la mayoría de los candidatos menores.
14!/9!
, pero para hasta 5 de 14 opciones clasificadas es en realidad SUM(14!/(14-n)!) for n=1 to 5
lo que podría calcular en Excel, pero aún así,... El punto es que no importa para esto.Tengo curiosidad por saber cómo la ciudad de Nueva York implementará física y computacionalmente el conteo de votos por orden de preferencia.
Físicamente , los votantes recibieron una boleta tabular (consulte esta página del gobierno de la Ciudad de Nueva York )donde las filas son candidatos y las columnas están en orden de preferencia, y las boletas se escanean para obtener registros de longitud variable (el votante puede expresar 1÷5 opciones) que contienen los candidatos votados en orden de preferencia.
Computacionalmente , NYC tiene una versión más a prueba de fallas de este script de Python (relativamente) simple
from random import seed, shuffle
from timeit import default_timer as dt
seed(20210622)
n_candidates, n_choices, n_ballots = 14, 5, 10**6
# ##### generate the ballots
start_generation = dt()
candidates = list(range(n_candidates))+[0] # introducing a bias for candidate 0
ballots = [candidates[:n_choices] for _ in range(n_ballots)
if not shuffle(candidates)]
print("\nGeneration of %d ballots required %.2f s"%(
n_ballots, dt()-start_generation))
# ##### process the ballots
start_count = dt()
while True:
counts = {candidate:0 for candidate in candidates}
# count 1st choices
for ballot in ballots: counts[ballot[0]] += 1
# sort candidates according to 1st choices
ranks = sorted(list(counts.items()), key=lambda t:t[1])
# max no. of 1st choices
max_1st = ranks[-1][1]
# if there is a winner, stop counting
if max_1st > len(ballots)//2: break
# who is the loser?
loser = ranks[0][0]
# remove loser from ballots and from list of candidates
for ballot in ballots:
if loser in ballot: ballot.remove(loser)
candidates.remove(loser)
# remove any empty ballot from list of ballots
# (copying not empty ballots is WAY FASTER than deleting void ballots)
ballots = [ballot for ballot in ballots if ballot]
# we have a winner
print(*reversed(ranks), sep='\n')
print("Counting %d ballots required %.2f s"%(
n_ballots, dt()-start_count))
Cuando lo ejecuté en mi antiguo portátil de gama baja, obtuve el siguiente resultado
Generation of 1000000 ballots required 9.29 s
(0, 490711)
(12, 245897)
Counting 1000000 ballots required 6.08 s
Incluso en esta simulación es evidente que el verdadero problema es preparar los datos en un formato que sea adecuado para contar, entonces es cuestión de segundos...
Como nota al pie, inicialmente pensé que tenía que optimizar el script usando bibliotecas matemáticas vectoriales, pero resultó que no era necesario.
+n!
, pero me pregunto si la detección y el manejo de clasificaciones faltantes (por ejemplo, solo 2, 3 y 5) o repeticiones (por ejemplo, 1: "X", 2: "Y", 3 : "X") es una parte importante del proceso? No pregunté específicamente sobre eso, pero como publicaste un algoritmo de ejemplo, debería representar de alguna manera cada uno de los elementos críticos.s/- 3 - 7 2/3 7 2 - -/
". Lo mismo se aplica a las repeticiones, pero aquí la página que vinculé dice que las repeticiones simplemente se ignoran, por lo que debería ser s/3 3 3 12 1/3 12 1 - -/
. Finalmente, se tratan registros de diferentes longitudes durante el procesamiento, por lo que puedo decir que también se pueden tratar registros de diferentes longitudes en el primer paso.
Filósofos italianos 4 Monica
UH oh
alfa draconis
Filósofos italianos 4 Monica
UH oh
UH oh
gidds
chris h
UH oh
phoog
UH oh
robert bristow-johnson