class Car{
    constructor(x,y,width,height,controlType,maxSpeed=3){
       this.x=x;
       this.y=y;
       this.width=width;
       this.height=height;
 
       this.speed=0;
       this.acceleration=0.2;
       this.maxSpeed=maxSpeed;
       this.friction=0.05;
       this.angle=0;
 
       this.damaged=false;
 
       this.useBrain=controlType=="AI";
 
       if(controlType!="DUMMY"){
          this.sensor=new Sensor();
          this.brain=new NeuralNetwork(
             [this.sensor.rayCount,4]
          );        
       }
       this.controls=new Controls(controlType);
    }
 
    update(roadBorders,traffic){
       if(!this.damaged){
          this.#move();  
          this.polygon=this.#createPolygon();
          this.damaged=this.#assessDamage(roadBorders,traffic);
       }
       if(this.sensor){
          this.sensor.update(this.x,this.y,this.angle,roadBorders,traffic);
          const offsets=this.sensor.readings.map(
             s=>s==null?0:1-s.offset
          );
          const outputs=NeuralNetwork.feedForward(offsets,this.brain);
          if(this.useBrain){
             this.controls.forward=outputs[0];
             this.controls.left=outputs[1];
             this.controls.right=outputs[2];
             this.controls.reverse=outputs[3];
          }
       }
    }
 
    #assessDamage(roadBorders,traffic){
       for(let i=0;i<roadBorders.length;i++){
          if(polysIntersect(
                [...this.polygon,this.polygon[0]],
                roadBorders[i])
             ){
             return true;
          }
       }
       for(let i=0;i<traffic.length;i++){
          const poly=traffic[i].polygon;
          if(polysIntersect(
                [...this.polygon,this.polygon[0]],
                [...poly,poly[0]])
             ){
             return true;
          }
       }
       return false;
    }
 
    #createPolygon(){
       const points=[];
       const rad=Math.hypot(this.width,this.height)/2;
       const alpha=Math.atan2(this.width,this.height);
       points.push({
          x:this.x-Math.sin(this.angle-alpha)*rad,
          y:this.y-Math.cos(this.angle-alpha)*rad
       });
       points.push({
          x:this.x-Math.sin(this.angle+alpha)*rad,
          y:this.y-Math.cos(this.angle+alpha)*rad
       });
       points.push({
          x:this.x-Math.sin(Math.PI+this.angle-alpha)*rad,
          y:this.y-Math.cos(Math.PI+this.angle-alpha)*rad
       });
       points.push({
          x:this.x-Math.sin(Math.PI+this.angle+alpha)*rad,
          y:this.y-Math.cos(Math.PI+this.angle+alpha)*rad
       });
       return points;
    }
 
    #move(){
       if(this.controls.forward){
          this.speed+=this.acceleration;
       }
       if(this.controls.reverse){
          this.speed-=this.acceleration;
       }
       
       if(this.speed!=0){
          const flip=this.speed>0?1:-1;
          if(this.controls.left){
             this.angle+=0.03*flip;
          }
          if(this.controls.right){
             this.angle-=0.03*flip;
          }
       }
 
       if(this.speed>this.maxSpeed){
          this.speed=this.maxSpeed;
       }
       if(this.speed<-this.maxSpeed/2){
          this.speed=-this.maxSpeed/2;
       }
 
       if(this.speed>0){
          this.speed-=this.friction;
       }
       if(this.speed<0){
          this.speed+=this.friction;
       }
       if(Math.abs(this.speed)<this.friction){
          this.speed=0;
       }
 
       this.x-=Math.sin(this.angle)*this.speed;
       this.y-=Math.cos(this.angle)*this.speed;
    }
 
    draw(ctx,drawSensor=false){
       if(this.damaged){
          ctx.fillStyle="gray";
       }else{
          ctx.fillStyle="black";
       }
       ctx.beginPath();
       ctx.moveTo(this.polygon[0].x,this.polygon[0].y);
       for(let i=1;i<this.polygon.length;i++){
          ctx.lineTo(this.polygon[i].x,this.polygon[i].y);
       }
       ctx.fill();
       if(this.sensor && drawSensor){
          this.sensor.draw(ctx);
       }
    }
 }Economic paradoxes
Sure! Here's a list of 100 economic paradoxes, each in one concise line: ๐ฐ 1–20: Classic & Popular Economic Paradoxes Paradox of Thrift – More saving reduces overall savings in a recession. Jevons Paradox – More efficiency in energy leads to more total consumption. Gibson’s Paradox – Interest rates rise with prices, not inflation. Lucas Paradox – Capital doesn’t flow to poorer nations as expected. Productivity Paradox – Tech improves, but measured productivity lags. Easterlin Paradox – More income doesn’t always mean more happiness. Voting Paradox – Rational people vote despite it not being individually beneficial. Leontief Paradox – The U.S. exports labor-intensive goods despite being capital-rich. Paradox of Value – Water is vital but cheap; diamonds are useless but expensive. Backfire Effect – People may double down on beliefs when given facts. Paradox of Plenty (Resource Curse) – Natural riches often lead to slower growth. Tragedy of the Commons – Shared resources get over...
 
 
Comments
Post a Comment