计算直线的交点数(set + 打表)

本文深入分析了在平面上给定n条直线时,它们所能形成的交点总数的计算方法,并提供了相应的代码实现。通过枚举平行线的条数,结合集合操作,有效地计算出了所有可能的交点数方案。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

计算直线的交点数

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 9357    Accepted Submission(s): 4226

Problem Description
平面上有n条直线,且无三线共点,问这些直线能有多少种不同交点数。 比如,如果n=2,则可能的交点数量为0(平行)或者1(不平行)。
 

 

Input
输入数据包含多个测试实例,每个测试实例占一行,每行包含一个正整数n(n<=20),n表示直线的数量.
 

 

Output
每个测试实例对应一行输出,从小到大列出所有相交方案,其中每个数为可能的交点数,每行的整数之间用一个空格隔开。
 

 

Sample Input
2 3
 

 

Sample Output
0 1 0 2 3
 

题解:用st存一下i条直线的点数目的种类;然后枚举平行线的条数j;当前点的个数就是*iter+平行的*不平行的,画个图看下就好了;

想了下,写下就过了;有点dp的意思

代码:

#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
#include<algorithm>
#include<set>
using namespace std;
set<int>st[25];
set<int>::iterator iter;
void db(){
    st[1].insert(0);
    for(int i = 2; i < 25; i++){
        st[i].insert(0);
        for(int j = 1; j < i; j++){
            for(iter = st[i - j].begin(); iter != st[i - j].end(); iter++){
                int dot = *iter + (i - j) * j;
                    st[i].insert(dot); 
            }
        }
    }
    
}
int main(){
    int n;
    db();
    while(~scanf("%d", &n)){
        for(iter = st[n].begin(); iter != st[n].end(); iter++){
            if(iter != st[n].begin())printf(" ");
            printf("%d", *iter);
        }
        puts("");
    }
    return 0;
}

 java:

package com.lanqiao.week1;

import java.util.Arrays;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Scanner;
import java.util.Set;

public class hdu1466 {
    private static Scanner cin = null;
    static Set<MyInteger>[] set = null;
    static MyInteger[][] arr = new MyInteger[25][];
    private static final int MAXN = 25;
    static{
        cin = new Scanner(System.in);
        set = new HashSet[MAXN];
    }
    static class MyInteger implements Comparable{
        int v;
        @Override
        public int hashCode() {
            return v;
        }
        public int getV() {
            return v;
        }
        public MyInteger(int v) {
            super();
            this.v = v;
        }
        @Override
        public String toString() {
            return v + "";
        }
        @Override
        public boolean equals(Object obj) {
            MyInteger t = (MyInteger)obj;
            return t.v == this.v;
        }
        @Override
        public int compareTo(Object o) {
            MyInteger t = (MyInteger)o;
            return this.v - t.getV();
        }
    }
    private static void getSet(){
        for(int i = 0; i < MAXN; i++){
            set[i] = new HashSet<MyInteger>(){};
        }
        set[1].add(new MyInteger(0));
        for(int i = 2; i < MAXN; i++){
            set[i].add(new MyInteger(0));
            for(int j = 1; j < i; j++){
                Iterator<MyInteger> iter = set[i - j].iterator();
                while(iter.hasNext()){
                    //System.out.println("zz");
                    set[i].add(new MyInteger(iter.next().getV() + j * (i - j)));
                }
            }
        }
        for(int i = 1; i < MAXN; i++){
            arr[i] = new MyInteger[set[i].size()];
            set[i].toArray(arr[i]);
            Arrays.sort(arr[i]);
        }
    }
    public static void main(String[] args) {
        getSet();
        while(cin.hasNext()){
            int N = cin.nextInt();
            
            for(int i = 0; i < arr[N].length; i++){
                if(i != 0){
                    System.out.print(" ");
                }
                System.out.print(arr[N][i].getV());
            }System.out.println();
        }
    }
}

 

### 计算两条直线交点 在 Manim 中虽然没有直接提供计算直线交点的功能,但是可以通过学方法来实现这一目标。对于给定的两条直线方程 \(y = m_1x + c_1\) 和 \(y = m_2x + c_2\), 如果这两条直线不平行,则它们有唯一的交点 \((x_i, y_i)\),该交点满足: \[m_1x_i + c_1 = m_2x_i + c_2\] 解这个方程可得: \[x_i = (c_2 - c_1)/(m_1-m_2)\] 再代入任一直线方程得到对应的\(y_i\)值。 为了更贴近实际应用,在图像处理场景下,当涉及到通过Hough变换检测到的线条时[^2],这些线条可能不是完美的无限延伸的理想化模型而是有限长度的实际图形对象。此时,应该先获取每一条线段两端点的世界坐标表示形式,进而利用上述公式求取理论上的交点位置;如果此交点确实位于两条线段所限定范围内则认为有效。 下面是一个简单的Python代码片段展示如何基于Manim库创建这样的功能: ```python from manim import * def find_intersection(line1_start, line1_end, line2_start, line2_end): """Calculate the intersection of two lines defined by start and end points.""" def det(a, b): return a[0]*b[1]-a[1]*b[0] xdiff = (line1_start[0] - line1_end[0], line2_start[0] - line2_end[0]) ydiff = (line1_start[1] - line1_end[1], line2_start[1] - line2_end[1]) div = det(xdiff, ydiff) if div == 0: raise Exception('lines do not intersect') d = (det(*[(line1_start[i], line1_end[i]) for i in range(2)]), det(*[(line2_start[i], line2_end[i]) for i in range(2)])) x = det(d, xdiff) / div y = det(d, ydiff) / div return np.array([x,y,0]) class IntersectionExample(Scene): def construct(self): axes = Axes() l1 = Line(start=[-4,-2,0],end=[2,3,0]).set_color(BLUE_C) l2 = Line(start=[-3,1,0],end=[3,-1,0]).set_color(GREEN_E) inter_point_coords = find_intersection([-4,-2,0],[2,3,0],[-3,1,0],[3,-1,0]) dot_at_interseciton = Dot(inter_point_coords).scale(2).set_fill(PINK, opacity=1) self.add(axes,l1,l2,dot_at_interseciton) ``` 这段代码首先定义了一个`find_intersection()`函用来接收四组参作为输入——即代表两条不同线段起点终点坐标的组,并返回一个由这两个实体相形成的单一点的位置向量。接着构建了一个名为 `IntersectionExample` 的场景实例,其中包含了两个具有特定颜色区分度的线段以及标记两者汇处的小粉圈。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值