Javascript 通过基于位置比较的数组切片,随机获取三个位置
我有一个数组,从中随机抽取3个位置。第三个位置不能是餐厅。当您看到代码时,这将是有意义的 我想做的是确保每个位置距离前一个位置至少1英里 代码: 这是我现有的代码。目前它有三个位置,但它们可能非常接近Javascript 通过基于位置比较的数组切片,随机获取三个位置,javascript,arrays,loops,sorting,random,Javascript,Arrays,Loops,Sorting,Random,我有一个数组,从中随机抽取3个位置。第三个位置不能是餐厅。当您看到代码时,这将是有意义的 我想做的是确保每个位置距离前一个位置至少1英里 代码: 这是我现有的代码。目前它有三个位置,但它们可能非常接近 for (let i = a.length - 1; i > 0; i--) { const j = Math.floor(Math.random() * (i + 1)); [a[i], a[j]] = [a[j], a[i]]; } let third = a[0]; l
for (let i = a.length - 1; i > 0; i--) {
const j = Math.floor(Math.random() * (i + 1));
[a[i], a[j]] = [a[j], a[i]];
}
let third = a[0];
let [first, second] = a.filter(l => !l.restaurant).slice(1);
let selectedLocations = [first, second, third];
function calculateDistance(lat1, lon1, lat2, lon2) {
let Rm = 3961;
let Rk = 6373
lat1 = deg2rad(lat1);
lon1 = deg2rad(lon1);
lat2 = deg2rad(lat2);
lon2 = deg2rad(lon2);
let dlat = lat2 - lat1;
let dlon = lon2 - lon1;
let a = Math.pow(Math.sin(dlat/2),2) + Math.cos(lat1) * Math.cos(lat2) * Math.pow(Math.sin(dlon/2),2);
let c = 2 * Math.atan2(Math.sqrt(a),Math.sqrt(1-a)); // great circle distance in radians
let dm = c * Rm; // great circle distance in miles
let dk = c * Rk; // great circle distance in km
let mi = round(dm);
let km = round(dk);
let ft = Math.round(mi * 5280.0);
return mi
}
function deg2rad(deg) {
let rad = deg * Math.PI/180; // radians = degrees * pi/180
return rad;
}
function round(x) {
return Math.round( x * 100) / 100;
}
记住(第三个)位置是第一个。一旦我有了第三个位置,我想通过阵列,直到我找到另一个位置,至少距离第三个位置1英里
这个新位置将成为(第二个)位置,一旦我有了这个位置(第二个),我需要再次检查阵列,并在至少1英里之外找到一个。这将是最终(第一个)位置
更新:
这里有一些与我所说的大致相同的东西,但我知道必须有一种更干净的写作方式
for (let i = a.length - 1; i > 0; i--) {
const j = Math.floor(Math.random() * (i + 1));
[a[i], a[j]] = [a[j], a[i]];
}
// We get our third location.
let third = a[0];
console.log(third)
// Build a new array removing the third location and
// any other locations that is a restaurant
let newarray = a.filter(l => !l.restaurant).slice(1);
// filter our new array based on the location being at
// least 1 mile away from the third location
let second = newarray.filter(function (e) {
return calculateDistance(
third.geolocation.lat,
third.geolocation.lng,
e.geolocation.lat,
e.geolocation.lng
) >= 1
})
// We now have our second location
console.log(second[0]);
// build a new array removing the second location
let thirdarray = second.slice(1);
// filter our new array based on the location being at
// least 1 mile away from the second location
let first = thirdarray.filter(function (e) {
return calculateDistance(
second[0].geolocation.lat,
second[0].geolocation.lng,
e.geolocation.lat,
e.geolocation.lng
) >= 1
})
// we now have our first location
console.log(first[0]);
根据我在评论中发布的链接,我提供了一个小型库来满足您的需求:
//{
const x=新的XMLHttpRequest;
const c=上下文| | this;
x、 打开('GET',url);
x、 onload=()=>{
if(success)success.call(c,JSON.parse(x.responseText));
}
x、 send();
}
post=(url、发送、成功、上下文)=>{
const x=新的XMLHttpRequest;
const c=上下文| | this;
x、 打开('POST',url);
x、 onload=()=>{
if(success)success.call(c,JSON.parse(x.responseText));
}
if(typeof send=='object'&&send&!(数组的发送实例)){
if(FormData的类型!==“未定义”&&send instanceof FormData){
x、 发送(send);
}
否则{
设s,r=[];
for(让p发送){
s=发送[p];
if(typeof s==='object')s=JSON.stringify(s);
r、 推送(encodeURIComponent(p)+'='+encodeURIComponent(s));
}
x、 setRequestHeader('Content-type','application/x-www-form-urlencoded');x.send(r.join('&');
}
}
否则{
抛出新错误(“发送参数必须是对象”);
}
返回x;
}
doc=文件;htm=doc.documentElement;bod=文件正文;导航=导航器;M=tag=>doc.createElement(标记);I=id=>doc.getElementById(id);
mobile=nav.userAgent.match(/Mobi/i)?真:假;
S=(选择器,在范围内)=>{
常数w=在| | doc内;
返回w.querySelector(选择器);
}
Q=(选择器,内部)=>{
常数w=在| | doc内;
返回w.querySelectorAll(选择器);
}
rad=n=>n*Math.PI/180;
距离=(车距、收费)=>{
设ll=latLng,ll=toLatLng;
if(ll instanceof数组){
ll={lat:ll[0],lng:ll[1]};
}
if(lL instanceof数组){
lL={lat:lL[0],lng:lL[1]};
}
常量lng1=ll.lng==未定义?+ll.lon:+ll.lng;
常量lng2=lL.lng==未定义?+lL.lon:+lL.lng;
常数m=6371e3,lat1=+ll.lat,lat2=+ll.lat,lat1R=rad(lat1);
常数lat2R=rad(lat2),latD=rad(lat2-lat1),lngD=rad(lng2-lng1);
常数n=Math.pow(Math.sin(latD/2),2)+Math.cos(lat1R)*Math.cos(lat2R)*Math.pow(Math.sin(lngD/2),2;
返回m*2*Math.atan2(Math.sqrt(n),Math.sqrt(1-n));
}
withinOneMile=(latLng,toLatLng)=>{
如果(距离(车床、托拉车)*3.2808/5280{
const cities=citiesArrayOfObjs.slice(),baseLatLng=cities.splice(originIndex,1)[0]。latLng,dists=[];
城市。forEach(o=>{
距离推送({城市:o.city,米:距离(baseLatLng,o.latLng)});
});
距离排序((a,b)=>a.meters-b.meters);
返回区;
}
//您可以将下面的内容放在另一页上-除了结束加载之外
const cities=[{城市:'西雅图',拉丁语:[47.6038321,-122.3300624]},{城市:'纽约',拉丁语:[40.7127281,-74.0060152]},{城市:'芝加哥',拉丁语:[41.8755616,-87.6244212]},{城市:'旧金山',拉丁语:[37.7790262,-122.4199061]};
const meterDists=sortCityDists(cities).reverse(),mileDists=[];
console.log(meterDists);
MeterSts.forEach(o=>{
mileDists.push({city:o.city,miles:o.meters*3.2808/5280});
});
控制台日志(mileDists);
常数locs=[[47.6038321,-122.3300624],[47.6038321,-122.3500624],[47.6038321,-122.3800624],[res=[];
对于(让i=0,n=1,loc1,loc2,l=locs.length;n
@StackSlave我不确定你的建议是什么?我的代码在上面。在代码中,我需要添加比较方面。如果你在问题中包含一些示例数据,这将非常有帮助。另外,你如何处理没有三个位置至少相隔一英里的情况?你能做到吗ion 1和位置3之间的距离不超过一英里,只要它们都离位置2一英里就可以了?@fubar位置1和3离得很近,我可以接受。我只需要1和2之间的距离以及2和3之间的距离至少为1英里。@fubar我更新了我的问题,以展示我正在努力实现的一个示例。我确信他们的答案是肯定的e是一种更好的编写方法。:)Thx StackSlave,但不幸的是,这并不能解决我的问题。我的代码可以工作。它捕获3个随机位置。我只需要向其中添加一个新变量。我需要每个位置至少相隔1英里。这就像yourArray[Math.floor(Math.random()*yourArray.length]一样简单
获取一个随机数组元素。因此,这应该不难。使用我的距离
函数计算距离。您可以传入两个[lat,lng]数组
,如果你愿意的话。那么你需要我们做什么?我会更新代码。我正在尝试在混合中添加一个新变量。我希望位置1和2至少相距1英里,位置2和3至少相距1英里。我正在试图找出实现这一点的最佳方法,以进一步解释。我的代码随机捕获3个位置。它是通过随机化数组,抓取第一个对象,然后过滤剩余对象,使其不包括餐厅,然后抓取接下来的两个位置来实现这一点。