commit cfa1f6fa3fd4f4c7afd3aaed998c8cdc5c95dfd1 Author: Teppy Date: Thu Sep 28 14:57:13 2023 -0400 Initial commit diff --git a/rangevote.html b/rangevote.html new file mode 100644 index 0000000..464d618 --- /dev/null +++ b/rangevote.html @@ -0,0 +1,51 @@ + + + + + + POST DEMO + + + +
+ This page is an experiment in voting. Half of the people who visit this site vote using Plurality Voting + where a voter selects their top candidate, and the winner is the candidate with the most votes. The other + half use Range Voting where voters score all familiar candidates based on how happy they would be should + that candidate win. You have been randomly selected to vote using Range Voting. +
+
+ + + + + + + + +
Candidate Happiness
+ +
+ +
+ + + diff --git a/rangevote.js b/rangevote.js new file mode 100644 index 0000000..2007b1c --- /dev/null +++ b/rangevote.js @@ -0,0 +1,141 @@ +var express = require('express') +var bodyParser = require('body-parser') +var fs=require('fs') + +var app = express() + + +var Candidates=[ "Chris Christie", "Ron DeSantis", "Nikki Haley", "Mike Pence", + "Vivek Ramaswamy", "Tim Scott", "Donald Trump" ]; + +function CanId(c) +{ + let w=c.split(" "); + let lastname=w[w.length-1].toLowerCase(); + let id=lastname.split("-"); + let rval=id[id.length-1]; + return(rval); +} + +// Set up data structures for Range Votes and Plur Votes +var RangeVotes=new Map(); +var RangePower=new Map(); +var RangeResult=new Map(); +var PlurVotes=new Map(); +var PlurResult=new Map(); +for (let c of Candidates) +{ + let k=CanId(c); + let v=RangePower.get(k); + if (typeof(v)!='number' || v==NaN || v==Infinity) RangePower.set(k,0); + v=RangeResult.get(k); + if (typeof(v)!='number' || v==NaN || v==Infinity) RangeResult.set(k,0); + v=PlurResult.get(k); + if (typeof(v)!='number' || v==NaN || v==Infinity) PlurResult.set(k,0); +} + + + +// Construct the static page for range voting +var TheHTML=""; +for (let c of Candidates) +{ + TheHTML=TheHTML+' '+ + ' '+c+'No Opinion\n'; +} +var TemplateHTML=fs.readFileSync("rangevote.html").toString(); +var TemplateSearch=""; +var TemplateIndex=TemplateHTML.indexOf(TemplateSearch); +TheHTML=TemplateHTML.substr(0,TemplateIndex)+TheHTML+TemplateHTML.substr(TemplateIndex+TemplateSearch.length,1000000); + + +// create application/json parser +var jsonParser = bodyParser.json() + +// create application/x-www-form-urlencoded parser +var urlencodedParser = bodyParser.urlencoded({ extended: false }) + +app.get('/', (req, res) => { + res.send(TheHTML); +}) + +function lerp(a,b,c,d,e) +{ + if (ac) a=c; + let rval=d+(a-b)*(e-d)/(c-b); + return(rval); +} + +function PlurVote(ip,NewChoice) +{ + let OldChoice=PlurResult.get(ip); + if (typeof(OldChoice)=='string') PlurResult.set(OldChoice,PlurResult.get(OldChoice)-1); + if (typeof(NewChoice)=='string') PlurResult.set(NewChoice,PlurResult.get(NewChoice)+1); +} + + +function AddToRangeResult(vote,mult=1) +{ + console.log("RangeResult Before "+mult); + console.log(RangeResult); + console.log("RangePower Before "+mult); + console.log(RangePower); + for (let[key,val] of vote) if (key) if (val>=0) + { + RangeResult.set(key,RangeResult.get(key)+val*mult); + RangePower.set(key,RangePower.get(key)+mult); + } + console.log("RangeResult After "+mult); + console.log(RangeResult); + console.log("RangePower After "+mult); + console.log(RangePower); +} + + +function RangeVote(ip,entries) +{ + let r0=null,r1=null; + for (let [key,val] of entries) if (typeof(key)=="string" && val>=0) + { + if (r0) r0=Math.min(r0,val); else r0=val; + if (r1) r1=Math.max(r1,val); else r1=val; + } + if (r1<=r0) return; + let NewVote=new Map() + for (let [key,val] of entries) if (typeof(key)=="string") + { + let id=CanId(key); + console.log(key+' '+id); + let norm=Math.round(lerp(val,r0,r1,0,100)); + if (val>=0) NewVote.set(id,norm); + } + let OldVote=RangeVotes.get(ip); +// if (OldVote) AddToRangeResult(OldVote,-1); + console.log("NewVote"); + console.log(NewVote); + RangeVotes.set(ip,NewVote); + AddToRangeResult(NewVote,1); +} + + +// POST /login gets urlencoded bodies +app.post('/range_vote', urlencodedParser, function (req, res) { + RangeVote(req.socket.remoteAddress,Object.entries(req.body)); + let str="Results:
"; + for (let c of Candidates) + { + let key=CanId(c); + if (RangePower.get(key)>0) str=str+c+': '+Math.round(RangeResult.get(key)/RangePower.get(key))+'
'; + } + res.send(str); +}) + +app.post('/plur_vote', urlencodedParser, function (req, res) { +// PlurVote(req.socket.remoteAddress,Object.entries(req.body)); + res.send("Your Plurality Vote Counted!!!"); +}) + + +app.listen(3000,function(req,res) { console.log("Listening for connections"); }) +