开心的算法

    技术2022-05-20  27

         今天在新浪微博中关注到淘宝文初大师的发起的:#一天一技术分享#今日分享林信良的常见算法笔记,看了一个“蒙地卡罗法求PI”的算法感觉很有意思,感觉解题的思路真是鬼斧神工啊,思维的发散与开发,以乱数概率的方法求解问题,真是如原文所说的“虽然在精确度上有所疑虑,但其解题的思考方向却是个值得学习的方式。”

     

     

    Algorithm Gossip: 蒙地卡罗法求PI

     说明

    蒙地卡罗为摩洛哥王国之首都,该国位于法国与义大利国境,以赌博闻名。 蒙地卡罗的基本原理为以乱数配合面积公式来进行解题,这种以机率来解题的方式带有赌博的意味,虽然在精确度上有所疑虑,但其解题的思考方向却是个值得学习的方式。

    解法

    蒙地卡罗的解法适用于与面积有关的题目,例如求PI值或椭圆面积,这边介绍如何求PI值;假设有一个圆半径为1,所以四分之一圆面积就为PI/4(原文此处可能有误),而包括此四分之一圆的正方形面积就为1,如下图所示:  如果随意的在正方形中投射飞标(点)好了,则这些飞标(点)有些会落于四分之一圆内,假设所投射的飞标(点)有n点,在圆内的飞标(点)有c点,则依比例来算,就会得到上图中最后的公式。至于如何判断所产生的点落于圆内,很简单,令乱数产生X与Y两个数值,如果X^2+Y^2小于1就是落在圆内。 

    实作: C     Java     Python     Scala

    C #include <stdio.h> #include <stdlib.h> #include <time.h> #define N 50000 int main(void) { srand(time(NULL)); int sum = 0; int i; for(i = 1; i < N; i++) { double x = (double) rand() / RAND_MAX; double y = (double) rand() / RAND_MAX; if((x * x + y * y) < 1) sum++; } printf("PI = %f/n", (double) 4 * sum / N); return 0; } Java import static java.lang.Math.*;public class Main { public static void main(String[] args) { final int N = 50000; int sum = 0; for(int i = 1; i < N; i++) if((pow(random(), 2) + pow(random(), 2)) < 1) sum++; System.out.printf("PI = %f%n", 4.0 * sum / N); }} Python import randomN = 50000sum = 0for i in range(1, N): if (random.random() ** 2 + random.random() ** 2) < 1: sum += 1print("PI = ", 4 * sum / N) Scala import java.lang.Math._val N = 50000var sum = 0for( i <- 1 until N if (pow(random(), 2) + pow(random(), 2)) < 1) sum += 1printf("PI = %f%n", 4.0 * sum / N); 特分享下啊:原文及更多:http://caterpillar.onlyfun.net/Gossip/AlgorithmGossip/AlgorithmGossip.htm


    最新回复(0)