【问题标题】:Divide the interval [0,1] into (3j-2) subintervals将区间 [0,1] 划分为 (3j-2) 个子区间
【发布时间】:2013-06-04 19:58:44
【问题描述】:

此代码在 [0,1) 范围内生成 50 个随机数。

int main(){

int i,j,M=50;

// If the interval is not uniform
double interval_widths[3] = { 0.1, 0.11, 0.03};

double interval_widths_sum[3];


//Divide into subintervals
void Init() {
  interval_widths_sum[0] = 0;
  for (int i=1; i<N; i++) {
    interval_widths_sum[i] = interval_widths_sum[i-1] + interval_widths[i];
  }
}

//check in which interval R is
int Seek(double R) {
  int i;
  if (R < 0.0) return -1;
  for (i = 0; i < N; i++) {
    if (R >= interval_widths_sum[i]) {
        break;
    }
   return (i);
  }

}

  unsigned long init[4] = {0x123, 0x234, 0x345, 0x456}, length = 4;

  MTRand drand; 

  for (i = 0; i < M; i++) {

    double x=("%10.8f ", drand());
    double y=("%10.8f ", drand());
    double R=("%10.8f ", drand());
    cout<<"(x,y)="<< x <<","<< y<< endl;
    a[i]=x*y;
       double *p= &x;
    double *q= &y;
    double *r= &R;
    double z= Seek(*r);
    cout<<"(x,y)="<<*p<<","<<*q<<endl;
    cout<< Init<<" "<< z<<endl;
  }
}

1) 在 [0,1] 范围内生成 x 和 y 的值。假设 x= 0.11, 0.23, ..... 和 y= 0.13, 0.33,.....等;

2) 现在定义 a= x*y。比如 a1= 0.11*0.13, a2 = 0.23*0.33 等。

3) 现在我想将区间 [0,1] 细分为 (3j-2) 大小为 [0,a1],[a1,a1+a2],......,[ai ,1] (i=1...3j-3)。

4) 然后生成[0,1]范围内的数R。并检查 (3j-2) 中的哪一个包含这个 R。

【问题讨论】:

    标签: c++ c algorithm random


    【解决方案1】:

    [编辑对 OP 目标的错误理解。希望现在更近了。]

    您有 N 个区间(框),其中N=(3*j-2)

    如果 j=1,您有 1 个角在 (0,0) 和 (1,1) 的盒子

    随机生成一个 x,y,每个都在 0.0 到 1.0 的范围内

    给定这个 x,y 找出 N 个盒子中的哪个包含这个点。查看每个现有的框,看看 (x,y) 是否在范围内。存在更快的方法,但这是一个起点。

    此时再细分这个盒子,这样就多了3个盒子。

    根据需要重复

    #include <ctype.h>
    #include <stdlib.h>
    #include <stdio.h>
    #include <memory.h>
    
    double drand() {
      return rand()/(1.0 + RAND_MAX);
    }
    
    
    typedef struct Box_s {
      double x0, y0, x1, y1;
    } Box_t;
    
    #define Box_N (303)
    int Box_Count = 0;
    Box_t Box[Box_N];
    
    void Box_Init() {
      memset(Box, 0, sizeof(Box));
      Box[0].x0 = 0.0;
      Box[0].y0 = 0.0;
      Box[0].x1 = 1.0;
      Box[0].y1 = 1.0;
      Box_Count = 1;
    }
    
    int Box_Find(double x, double y) {
      for (int b=0; b<Box_Count; b++) {
        if ((Box[b].x0 <= x) && (x <= Box[b].x1) && (Box[b].y0 <= y) && (y <= Box[b].y1)) {
          return b;
        }
      }
      printf("Box not found %e %e\n", x, y);
      exit(1);
    }
    
    void Box_Divide(int b, double x, double y) {
      if ((Box[b].x0 <= x) && (x <= Box[b].x1) && (Box[b].y0 <= y) && (y <= Box[b].y1)) {
        // Make 3 more boxes
        if ((Box_Count + 3) >= Box_N) {
          printf("Not enough boxes\n");
          exit(1);
        }
        Box[Box_Count].x0 = x;
        Box[Box_Count].x1 = Box[b].x1;
        Box[Box_Count].y0 = Box[b].y0;
        Box[Box_Count].y1 = y;
        Box_Count++;
        Box[Box_Count].x0 = x;
        Box[Box_Count].x1 = Box[b].x1;
        Box[Box_Count].y0 = y;
        Box[Box_Count].y1 = Box[b].y1;
        Box_Count++;
        Box[Box_Count].x0 = Box[b].x0;
        Box[Box_Count].x1 = x;
        Box[Box_Count].y0 = y;
        Box[Box_Count].y1 = Box[b].y1;
        Box_Count++;
        // Update original box
        Box[b].x1 = x;
        Box[b].y1 = y;
        return;
      }
      printf("x y not in box %d %e %e\n", b, x, y);
      exit(1);
    }
    
    
    void Box_Print() {
      double TotalArea = 0.0;
      printf("\n");
      printf("%3s (%5s, %5s) ( %5s, %5s) %5s\n", "#", "x0", "y0", "x1", "y1", "Area");
      for (int b=0; b<Box_Count; b++) {
        double Area = (Box[b].x0 - Box[b].x1) * (Box[b].y0 - Box[b].y1);
        printf("%3d (%5.3f, %5.3f) ( %5.3f, %5.3f) %5.3f\n", b, Box[b].x0, Box[b].x1, Box[b].y0, Box[b].y1, Area);
        TotalArea += Area;
      }
      printf("%3d  %5s  %5s    %5s  %5s  %5.3f\n", Box_Count, "", "", "", "", TotalArea);
    }
    
    int main(int argc, char *argv[]) {
      Box_Init();
      for (int rcount = 0; rcount < 50; rcount++) {
        Box_Print();
        double x = drand();
        double y = drand();
        int b = Box_Find(x, y);
        Box_Divide(b, x, y);
      }
      Box_Print();
      return 0;
    }
    

    【讨论】:

    • 谢谢。但是当我调用函数 Seek(double R) 时,它只返回'0'。我想要间隔号。我该如何解决?
    • 1) 确保在多次调用Seek() 之前调用一次Init()。或 2)请描述,也许编辑你的帖子,更多关于间隔细节。固定宽度? init[] 角色(我假设间隔宽度)? 3) 存在变体drand()。请确认您的drand() 生成随机double [0 到RAND_MAX) 或[0 到1)。
    • 我已经详细阐述了我的观点并编辑了我的帖子。请检查。
    • 1) 请解释[0,a1], [a1, a1+a2],...,[ai,1]?看来 sum a1+a2 可能超过 1.0。这个子区间[a1,a1+a2] 正确吗? 2) a1, a2, ... 是随机且未排序的。您是否希望间隔 [0,a1], [a1, a1+a2],...,[ai,1] 被排序而不重叠?
    • 1)由于我们采用 '[0,1]' 之间的值,因此总和不会超过 1.0 和 2)我希望它们不会重叠。考虑一个单位矩形和 ' a1,a2' 等是小矩形的区域。在 1st step 之后,它可能看起来像-bit.ly/15TsSw6。在第 6 步之后,单位正方形可能看起来像这样-bit.ly/11xyTOb
    猜你喜欢
    • 1970-01-01
    • 2020-08-25
    • 2016-05-07
    • 1970-01-01
    • 2019-04-14
    • 2018-05-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多