<?php
require_once dirname(__DIR__) . '/base/hypothesis.php';
require_once dirname(dirname(__DIR__)) . '/das/methods/vendor/autoload.php';
require_once dirname(dirname(__DIR__)) . '/zendasmath/basic/describe.php';
require_once dirname(dirname(__DIR__)) . '/zendasmath/distribution/studentT.php';

/**
 * Onesample
 */
class onesample extends hypothesis
{
    public $decimals;

    /**
     * Onesample chart μ method;
     *
     * @param string $var
     * @param string $type
     * @param bool $round
     * @access public
     * @return float
     */
    public function bar($data, $round = true)
    {
        Describe::$decimals = $this->decimals;
        return Describe::mean($data, $round);
    }

    /**
     * Onesample chart σ method;
     *
     * @param string $var
     * @param string $type
     * @param int    $index
     * @access public
     * @return array
     */
    public function sigma($data, $round = true)
    {
        Describe::$decimals = $this->decimals;
        return Describe::standard($data, $round);
    }

    /**
     * Onesample chart stDev method;
     *
     * @param string $col
     * @param string $type
     * @param bool $round
     * @access public
     * @return array
     */
    public function stDev($σ, $numCount)
    {
        $result   = $σ / sqrt($numCount);
        return $this->roundDigit($result);
    }

    /**
     * Onesample chart CI method;
     *
     * @param float  $μ
     * @param float  $σ
     * @param int    $numCount
     * @param float  $confidence
     * @param string $alterHypo
     * @access public
     * @return array
     */
    public function CI($μ, $σ,$numCount, $confidence, $alterHypo = 'ne', $round = true)
    {
        $α = (1 - $confidence / 100) / 2;
        if($alterHypo != 'ne') $α = $α* 2;

        $probability = 1 - $α;
        $degrees     = $numCount - 1;

        $studentT = new StudentT($degrees);
        $t        = $studentT->inverse($probability);
        $part     = abs($t) * $σ / sqrt($numCount);
        $LCL      = $μ - $part;
        $UCL      = $μ + $part;

        $LCL = $this->roundDigit($LCL);
        $UCL = $this->roundDigit($UCL);

        return array($LCL, $UCL);
    }

    /**
     * Onesample chart T method;
     *
     * @param float $μ
     * @param float $σ
     * @param int   $numCount
     * @param float $hypoMean
     * @access public
     * @return array
     */
    public function T($μ, $σ, $numCount, $hypoMean)
    {
        if($σ === 0) return '-';

        $result = ($μ - $hypoMean) / ($σ / sqrt($numCount));
        return $this->roundDigit($result);
    }

    /**
     * Onesample chart P method;
     *
     * @param float $t
     * @param int   $numCount
     * @param float $alterHypo
     * @access public
     * @return array
     */
    public function P($t, $numCount, $alterHypo)
    {
        if(!is_numeric($t)) return '-';

        $degrees  = $numCount - 1;
        $studentT = new StudentT($degrees);
        $cdf      = $studentT->cdf($t);

        if($alterHypo == 'lt')
        {
            $p = $cdf;
        }
        else if($alterHypo == 'gt')
        {
            $p = 1 - $cdf;
        }
        else
        {
            $p = $t > 0 ? 2 * (1 - $cdf) : (2 * $cdf);
        }

        return $this->roundDigit($p);
    }

    /**
     * Onesample chart getCITitle method;
     *
     * @param object $lang
     * @param float  $confidence
     * @param string $language
     * @access public
     * @return array
     */
    public function getCITitle($lang, $confidence, $language, $alterHypo)
    {
        $alterHypoName = array('lt' => 'upper', 'ne' => 'ci', 'gt' => 'lower');
        $name = $alterHypoName[$alterHypo];

        if($language == 'en') return $confidence . '% ' . $lang->$name . ' for μ';
        else return 'μ的' . $confidence . '%' . $lang->$name;
    }

    /**
     * Onesample chart getCIValue method;
     *
     * @param string $name
     * @param float  $confidence
     * @param object $lang
     * @access public
     * @return array
     */
    public function getCIValue($CI, $alterHypo)
    {
        if($alterHypo == 'lt')
        {
            return $CI[1];
        }
        else if($alterHypo == 'ne')
        {
            return '(' . $CI[0] . ', ' . $CI[1] . ')';
        }
        else if($alterHypo == 'gt')
        {
            return $CI[0];
        }
    }

    /**
     * Onesample chart getDesc method;
     *
     * @param float  $hypoMean
     * @param string $alterHypo
     * @param object $lang
     * @access public
     * @return array
     */
    public function getDesc($hypoMean, $alterHypo, $lang)
    {
        $alterHypoSign = array('lt' => '<', 'ne' => '≠', 'gt' => '>');
        $sign = $alterHypoSign[$alterHypo];

        $desc = sprintf($lang, $hypoMean, $sign, $hypoMean);
        return $desc;
    }

    /**
     * Onesample chart createColumns method;
     *
     * @param object $lang
     * @param array  $data
     * @access public
     * @return array
     */
    public function createColumns($lang, $data)
    {
        $columns = array();
        foreach($data as $langKey => $type)
        {
            $columns[] = array('label' => $lang->$langKey, 'type' => $type);
        }

        return $columns;
    }
}
