编程练习:Transmitters

为何保持编程的兴趣,还是找一些代码来写

看了 http://poj.org/problem?id=1106, 分析思路如下:


1)把坐标系原点定位为圆心,把其他点转化为极坐标

2)从第一个点开始,逐个查找满足所有落在下面区域内的点:此点到原点为起始边,半径为参数所给的半圆围成区域

3)所有点都扫描后给出最大覆盖的点数




package com.pnp.hello;

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.geom.Arc2D;

import javax.swing.JFrame;

public class Hello {
	
	static class My extends JFrame {
		 double circle_x = 250;
		 double circle_y = 250;
		 double circle_r = 35;
		
		double[][] in_points = new double[][]{
				{250, 280},
				{230, 270},
				{270, 270},
				{240, 230},
				{260, 230},
				{240, 290},
				{260, 290}
		};
		
		double[][] points = new double[in_points.length][2];
		double angles[] = new double[points.length];
		double dists[] =  new double[points.length];

		int max_count=0; // max point count
		int begin_index=-1; // the begin point of half circle
		int draw_index=0; // for drawing animation
		
		void cal () {
			// trans coordinate to polar coordinate
			for ( int i=0; i < points.length; i++ ) {
				points[i][0] = in_points[i][0] - circle_x;
				points[i][1] = in_points[i][1] - circle_y;
				angles[i] = Math.atan2(points[i][1], points[i][0]);
				dists[i] = Math.sqrt( points[i][0] * points[i][0] + points[i][1] * points[i][1] );
			}
			
			// count
			for ( int i=0; i < points.length; i++ ) {
				int count =0;
				for ( int j=0; j < points.length; j++) {
					double begin_a = angles[i];
					double end_a = begin_a + Math.PI;
					if ( angles[j] >= begin_a  &&  angles[j] <= end_a && dists[j] < circle_r)
						count++;
				}
				if ( count > max_count ) {
					max_count = count;
					begin_index = i;
				}
				
				// for animations effect
				draw_index = i;
				this.repaint();
				try {
					Thread.sleep(5000);
				} catch (InterruptedException e) {
					e.printStackTrace();
				}
			}
			
			this.repaint();
			draw_index = begin_index;
			System.out.printf("max_count: " + max_count  + "  begin_index: " + begin_index);

		}

		public void paint(Graphics g) {
			g.clearRect(0, 0, 500, 500);
			double ag = angles[draw_index];
			Arc2D arc = new Arc2D.Double(circle_x-circle_r, circle_y-circle_r, circle_r*2, circle_r*2, ag/Math.PI * 180, 180 , Arc2D.PIE);
			Graphics2D g2d = (Graphics2D) g;
			g2d.fill(arc);
			
			g.setColor(Color.RED);
			for ( int i=0; i < in_points.length; i++ ) {
				g.drawLine((int)in_points[i][0],(int)in_points[i][1] ,(int)in_points[i][0] + 1 , (int)in_points[i][1] +1 );
				//g.drawLine((int)circle_x-circle_r,(int)circle_y,(int)circle_x + circle_r , (int)circle_y );
			}
		}
	}
	
	public static void main(String[] args) {
		My frame = new Hello.My();
		frame.setTitle("half circle cover points");
		frame.setBounds(0, 0, 500, 500);
		frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		frame.setVisible(true);
		frame.cal();
				
	}
}




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值