Koch曲线的构造过程是:取一条长度为L0的直线段,将其三等分,保留两端的线段,将中间的一段改换成夹角为60度的两个等长直线;再将长度为L0/3的4个直线段分别进行三等分,并将它们中间的一段均改换成夹角为60度的两段长为L0/9的直线段;重复以上操作直至无穷,可得以一条具有自相似结构的折线,如图1所示。

图1  Koch曲线的生成

Koch曲线采用递归过程易于实现,编写如下的HTML代码。

<!DOCTYPE html>

<head>

<title>Koch曲线</title>

</head>

<body>

<canvas id="myCanvas" width="600" height="400" style="border:3px double #996633;">

</canvas>

<script type="text/javascript">

var canvas = document.getElementById('myCanvas');

var ctx = canvas.getContext('2d');

var maxdepth =5;

var curdepth = 0;

ctx.lineWidth = 2;

Koch({x:50,y:150},{x:550,y:150},Math.PI/3);

function Koch(p1,p2,angle)

{

curdepth++;

if (curdepth<=maxdepth)

{

var x1=(2*p1.x+p2.x)/3;

var y1=(2*p1.y+p2.y)/3;

var x3=(2*p2.x+p1.x)/3;

var y3=(2*p2.y+p1.y)/3;

var x2=(x3-x1)*Math.cos(angle)-(y3-y1)*Math.sin(angle)+x1;

var y2=(x3-x1)*Math.sin(angle)+(y3-y1)*Math.cos(angle)+y1;

Koch(p1,{x:x1,y:y1},Math.PI/3);

Koch({x:x1,y:y1},{x:x2,y:y2},Math.PI/3);

Koch({x:x2,y:y2},{x:x3,y:y3},Math.PI/3);

Koch({x:x3,y:y3},p2,Math.PI/3);

}

if (curdepth>maxdepth)

draw([p1,{x:x1,y:y1},{x:x2,y:y2},{x:x3,y:y3},p2]);

curdepth--;

}

function draw(points)

{

ctx.strokeStyle = "red";

ctx.beginPath()

ctx.moveTo(points[0].x,points[0].y)

for(i=1;i<points.length;i++)

{

ctx.lineTo(points[i].x,points[i].y);

}

ctx.closePath()

ctx.stroke()

}

</script>

</body>

</html>

在浏览器中打开包含这段HTML代码的html文件,可以看到在浏览器窗口中绘制出的Koch曲线,如图2所示。

图2  递归深度maxdepth =5的Koch曲线

由图1和2可知,Koch曲线的初始图元是直线,但最终结果却是一条参差不齐的曲线,很像雪花的边缘,如果将3条这样的曲线围在一起,便得到Koch雪花的图案。这样,初始图元不是一条直线,而是一个等边三角形。Koch雪花的生成示例如图3所示。

图3  Koch雪花的生成

在程序设计时,定义好等边三角形的三个顶点坐标,调用三次Koch递归过程,以实现等边三角形三条边各自的Koch曲线生成,即可得到Koch雪花图案。编写的HTML文件如下。

<!DOCTYPE html>

<head>

<title>Koch雪花</title>

</head>

<body>

<canvas id="myCanvas" width="600" height="600" style="border:3px double #996633;">

</canvas>

<script type="text/javascript">

var canvas = document.getElementById('myCanvas');

var ctx = canvas.getContext('2d');

var maxdepth =5;

var curdepth = 0;

ctx.lineWidth = 2;

Koch({x:50,y:450},{x:500,y:450},Math.PI/3);

Koch({x:275,y:450-225*Math.sqrt(3)},{x:50,y:450},Math.PI/3);

Koch({x:500,y:450},{x:275,y:450-225*Math.sqrt(3)},Math.PI/3);

function Koch(p1,p2,angle)

{

curdepth++;

if (curdepth<=maxdepth)

{

var x1=(2*p1.x+p2.x)/3;

var y1=(2*p1.y+p2.y)/3;

var x3=(2*p2.x+p1.x)/3;

var y3=(2*p2.y+p1.y)/3;

var x2=(x3-x1)*Math.cos(angle)-(y3-y1)*Math.sin(angle)+x1;

var y2=(x3-x1)*Math.sin(angle)+(y3-y1)*Math.cos(angle)+y1;

Koch(p1,{x:x1,y:y1},Math.PI/3);

Koch({x:x1,y:y1},{x:x2,y:y2},Math.PI/3);

Koch({x:x2,y:y2},{x:x3,y:y3},Math.PI/3);

Koch({x:x3,y:y3},p2,Math.PI/3);

}

if (curdepth>maxdepth)

draw([p1,{x:x1,y:y1},{x:x2,y:y2},{x:x3,y:y3},p2]);

curdepth--;

}

function draw(points)

{

ctx.strokeStyle = "red";

ctx.beginPath()

ctx.moveTo(points[0].x,points[0].y)

for(i=1;i<points.length;i++)

{

ctx.lineTo(points[i].x,points[i].y);

}

ctx.closePath()

ctx.stroke()

}

</script>

</body>

</html>

在浏览器中打开包含这段HTML代码的html文件,在浏览器窗口中可能会绘制出如图4所示的Koch雪花图案。

图4  递归深度maxdepth =5的Koch雪花图案

最新文章

  1. javascript数组的一些方法实例
  2. php启动时候提示PHP startup的解决方法
  3. [Codeforces673A]Bear and Game(水题,思路)
  4. Java bit、byte、位、字节、汉字、字符
  5. (二)Jquery Mobile介绍以及Jquery Mobile页面与对话框
  6. CCS学习(三)
  7. webpack2使用ch8-loader解析less less自动添加浏览器前缀
  8. 关于userInteractionEnabled的属性的理解
  9. Pyhton2.x 和Python3.x
  10. Wannafly挑战赛 22
  11. 我的物联网项目专题移到网站:http://51jdk.com
  12. Docker stop停止/remove删除所有容器
  13. Ubuntu16.04下编译安装及运行单目ORBSLAM2
  14. 峰Spring4学习(2)依赖注入的几种方式
  15. C++互斥器:Semaphores
  16. AI,DM,ML,PR的区别与联系
  17. ACM练习网站
  18. Learning Python 004 基础的数据类型和变量
  19. Picasso,Glide,Fresco那个好?
  20. 描述怎样通过flask+redis+sqlalchemy等工具,开发restful api

热门文章

  1. java实现最大连续和问题
  2. Java实现二分图的最大匹配
  3. LoadRunner性能测试笔试/面试题
  4. hiredis window 源码编译
  5. 软光栅-uraster代码阅读(入门极品)
  6. &lt;WP8开发学习笔记&gt;修改panorama全景控件的标题的大小
  7. 操作-写入excel
  8. 如何从二进制文件中读取int型序列
  9. Moco测试知多少?
  10. Hexo快速构建个人小站-Hexo初始化和将项目托管在Github(一)