[英]How to find y when x is given and a list of points?
There's a group: 有一个小组:
S = {(xi,yi)|1 ≤ i ≤ n}
of n points. 的n分。 There are no 2 points
(xi,yi) (xj,yj) where xi = xj and yi = yj
. 没有2个点
(xi,yi) (xj,yj) where xi = xj and yi = yj
。 It means the x and y values are unique. 这意味着x和y值是唯一的。 I need to find a data structure that supports the functions:
我需要找到一个支持这些功能的数据结构:
A simple solution will be to create two sorted arrays (one sorted according to the x values and the second sorted according to the y values). 一个简单的解决方案是创建两个排序的数组(一个根据x值排序,第二个根据y值排序)。 To find y with a given x will take
O(logn)
, by using binary search. 要使用给定的x查找y,将使用二进制搜索来获取
O(logn)
。 The same for finding x. 查找x相同。
I can't use more than one array (of n elements) and each element is a point . 我不能使用多个数组(包含n个元素),每个元素都是一个point 。 I need to find an efficient data structure that can do those actions in an optimal time.
我需要找到一个可以在最佳时间内执行这些操作的有效数据结构。 I need to find:
我需要找到:
T(first function)+T(second action)
. T(first function)+T(second action)
。
Which data structure is the most efficient in this case? 在这种情况下,哪种数据结构最有效?
Thank you very much. 非常感谢你。
Fundamentally, you just need a pair of maps: 从根本上讲,您只需要一对地图:
Map<TypeOfX, TypeOfY> mapXtoY;
Map<TypeOfY, TypeOfX> mapYtoX;
You can use any concrete implementation of Map
, eg HashMap
, TreeMap
, LinkedHashMap
... 您可以使用
Map
任何具体实现,例如HashMap
, TreeMap
, LinkedHashMap
...
To add a point, you simply add it to both: 要添加一个点,只需将其添加到两个位置:
void addPoint(TypeOfX x, TypeOfY y) {
mapXtoY.put(x, y);
mapYtoX.put(y, x);
}
And you can get the y
for an x
by using: 您可以使用以下方法获得
x
的y
:
TypeOfY y = mapXtoY.get(x);
and vice versa. 反之亦然。
Libraries such as Guava provide BiMap
implementations, which maintain this two-directional mapping for you. 番石榴(Guava)等库提供
BiMap
实现,可以为您维护此双向映射。
Note: I dont read your condition '(xi, yi), (xj, yj) => xi != xj && yi != yj' as you do, to me this only means that the coordinates are unique (not each x and each y). 注意:我不会像您那样阅读您的条件'(xi,yi),(xj,yj)=> xi!= xj && yi!= yj',对我而言,这仅意味着坐标是唯一的(不是每个x和每个y)。
So you first must create a Point object 因此,您首先必须创建一个Point对象
public class Point {
public int x;
public int y;
public Point(int x, int y) { this.x = x; this.y = y; }
}
Then store all your points into a unique array (you said you need it) 然后将所有点存储到一个唯一的数组中(您说过需要它)
Point[] POINTS = ... // fill your array depending on your input
Finally wrap ths array into a class that provides the methods you need 最后,将数组包装到提供所需方法的类中
public class PointCollection {
public Point[] points;
public Map<Integer, List<Integer>> mapX = new HashMap<Integer; List<Integer>>();
public Map<Integer, List<Integer>> mapY = new HashMap<Integer; List<Integer>>();
public PointCollection(Points[] points) {
this.points = points;
for (Point p : points) {
mapX.getOrDefault(p.x, new ArrayList<Integer>()).add(p.y);
mapY.getOrDefault(p.y, new ArrayList<Integer>()).add(p.x);
}
}
public int[] getMatchingY(int x) {
List<Integer> result = new ArrayList<Integer>();
for (Point p : this.points)) {
if (p.x == x) result.add(p.y);
}
return result.toArray(new int[result.size()]);
}
public int[] getMatchingX(int y) {
List<Integer> result = new ArrayList<Integer>();
for (Point p : this.points)) {
if (p.y == y) result.add(p.x);
}
return result.toArray(new int[result.size()]);
}
public int[] getMatchingYFromMap(int x) {
List<Integer> result = mapX.getOrDefault(x, new ArrayList<Integer>());
return result.toArray(new int[result.size()]);
}
public int[] getMatchingXFromMap(int y) {
List<Integer> result = mapY.getOrDefault(y, new ArrayList<Integer>());
return result.toArray(new int[result.size()]);
}
}
edit: added solution based on map 编辑:添加了基于地图的解决方案
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.