In case Flash no longer exists; a copy of this site is included in the Flashpoint archive's "ultimate" collection.

Dead Code Preservation :: Archived AS3 works from wonderfl.net

正規分布するような乱数

スライダーで偏差やらなんやら設定してRunで動く。
別アプリ用にパラメーターの試験用とかなんとか。ENTER_FRAME使わない方がツールとしては便利。
Get Adobe Flash player
by kske 12 Oct 2011
/**
 * Copyright kske ( http://wonderfl.net/user/kske )
 * MIT License ( http://www.opensource.org/licenses/mit-license.php )
 * Downloaded from: http://wonderfl.net/c/v0mm
 */

package {
    import com.bit101.components.Label;

    import flash.geom.Vector3D;
    import flash.geom.Rectangle;
    import flash.events.MouseEvent;
    import flash.events.Event;

    import com.bit101.components.Panel;
    import com.bit101.components.PushButton;
    import com.bit101.components.HSlider;

    import flash.display.BitmapData;
    import flash.display.Sprite;
    import flash.display.Bitmap;

    public class BMTest extends Sprite {
        private var canvas:BitmapData;
        private var bitmap:Bitmap;
        private var MeanSlider:HSlider;
        private var StdDevSlider:HSlider;
        private var runButton:PushButton;
        private var meanLabel:Label;
        private var devLabel:Label;
        private var activeParticles:Vector.<Particle>;
        private var restParticles:Vector.<Particle>;
        private static var MAX_SAMPLE:int = 10000;
        private static var CREATE_PER_FRAME:int = 5;
        private static var STEP_PER_FRAME:int = 4;
        private var samples:int;
        private var bmt:BMTRandom;
        private var values:Array;
        private var isStarted:Boolean;
        [SWF(backgoundColor=0x0, frameRate="60", width=465, height=465)]
        public function BMTest() {
            addEventListener(Event.ADDED_TO_STAGE, init);
            //run(0, 1, 0xff44ccc, canvas);
        }
        
        private function init(e:Event):void{
            removeEventListener(Event.ADDED_TO_STAGE, arguments.callee);
            canvas = new BitmapData(465, 465, true, 0xff000000);
            bitmap = new Bitmap(canvas);
            addChild(bitmap);
            
            isStarted = false;
            samples = 0;
            
            createControls();
        }
        
        // initが長くなりそうだからminimalcompsはこっちに
        private function createControls():void{
            MeanSlider = new HSlider(this, 10, 5);
            MeanSlider.maximum = 3;
            MeanSlider.minimum = -3;
            meanLabel = new Label(this, 110, 0, "0.0");
            StdDevSlider = new HSlider(this, 10, 17);
            StdDevSlider.maximum = 3;
            StdDevSlider.minimum = 0.2;
            devLabel = new Label(this, 110, 12, "0.2");
            MeanSlider.addEventListener(Event.CHANGE, MeanSliderChange);
            StdDevSlider.addEventListener(Event.CHANGE, DevSliderChange);
            runButton = new PushButton(this, 10, 29, "Run");
            runButton.addEventListener(MouseEvent.CLICK, onClick);
            
        }
        private function MeanSliderChange(e:Event):void
        {
            meanLabel.text = MeanSlider.value.toFixed(1);
        }
        private function DevSliderChange(e:Event):void
        {
            devLabel.text = StdDevSlider.value.toFixed(1);
        }
        
        private function onClick(e:Event):void{
            run(MeanSlider.value, StdDevSlider.value);
        }
        
        private function update(e:Event):void{
            var i:int;
            var j:int;
            for(j = 0; j < CREATE_PER_FRAME; j++){
                if(samples < MAX_SAMPLE){
                    activeParticles.push(createParticle());
                    samples++;
                }
            }
            
            canvas.lock();
            canvas.fillRect(new Rectangle(0, 0, 465, 465), 0xff000000);
            for(i = activeParticles.length - 1; i >= 0; i--){
                var p:Particle = activeParticles[i];
                
                p.y += BMTest.STEP_PER_FRAME;
                if(p.y >= p.distY){
                    p.y = p.distY; // いちおー
                    restParticles.push(p);
                    activeParticles.splice(i, 1);
                }else{
                    canvas.setPixel(p.x, p.y, 0x1144ee);
                }
            }
            
            drawRests();
            canvas.unlock();
        }
        
        private function drawRests():void{
            var i:uint; // 別BMP用意して一度描画して重ねちゃった方が早そう
            
            for(i = 0; i < restParticles.length; i++){
                var p:Particle = restParticles[i];
                canvas.setPixel(p.x, p.y, 0x3399ff);
            }
        }
        
        private function createParticle():Particle{
            var val:int;
            
            val = bmt.random() * 50;
            if(values[val]){
                values[val]++;
            }else{
                values[val] = 1;
            }
            
            return new Particle(val + 262, 0, val + 262, Math.max(465 - values[val], 0));
        }
        
        private function run(mean:Number, stdDev:Number):void{
            bmt = new BMTRandom(mean, stdDev);
            samples = 0;
            
            values = [];
            activeParticles = new Vector.<Particle>();
            restParticles = new Vector.<Particle>();
            
            if(!isStarted){
                addEventListener(Event.ENTER_FRAME, update);
                isStarted = true;
            }
        }

    }
}

class BMTRandom{
    private var result1:Number;
    private var result2:Number;
    private var isCached:Boolean;
    
    private var mean:Number;
    private var stdDev:Number;
    
    public function BMTRandom(_mean:Number, _stdDev:Number){
        isCached = false;
        
        mean = _mean;
        stdDev = _stdDev;
    }
    
    public function set Mean(_mean:Number):void{
        isCached = false;
        mean = _mean;
    }
    
    public function set StdDev(_stdDev:Number):void{
        isCached = false;
        stdDev = _stdDev;
    }
    
    public function get Mean():Number{
        return mean;
    }
    
    public function get StdDev():Number{
        return stdDev;
    }
    
    public function random():Number{
        var result:Number;
        if(isCached){
            isCached = false;
            result = normalDistribute(result2);
        }else{
            BMTransform();
            isCached = true;
            result = normalDistribute(result1);
        }
        return result;
    }

    
    private function normalDistribute(v:Number):Number{
        return v * stdDev + mean;
    }
    
    private function BMTransform():void{
        var n:Number = 0.0;
        var m:Number = Math.random();
        
        while(n == 0.0){
            n = Math.random();
        }
        
        result1 = Math.sqrt(-2 * Math.log(n)) * Math.sin( 2 * Math.PI * m);
        result2 = Math.sqrt(-2 * Math.log(n)) * Math.cos( 2 * Math.PI * m);

    }
}

class Particle{
    public var x:int;
    public var y:int;
    
    public var distX:int;
    public var distY:int;
    
    public function Particle(_x:int, _y:int, _distX:int, _distY:int){
        x = _x;
        y = _y;
        distX = _distX;
        distY = _distY;
    }
}