20种经纬度特征工程

1 两个经度/纬度的相减

使用相邻经度进行相减,相邻纬度相减,类似于经纬度的绝对变化特征

def lat_diff(lat1, lat2): 
    return lat1 - lat2
def lat_absdiff(lat1, lat2): 
    return abs(lat1 - lat2)
def lng_diff(lng1, lng2): 
    return lng1 - lng2
def lng_absdiff(lng1, lng2): 
    return abs(lng1 - lng2)

2 两个经度/纬度的相除

计算两个经度或者纬度的相除,减法如果是绝对特征,那么相除可以认为是相对特征

def lat_ratio(lat1, lat2): 
    return lat2 / lat1

def lgn_ratio(lgn1, lgn2): 
    return lgn2 / lgn1

3 经纬度相除

计算经纬度的相除的特征,类似于斜度计算

def lng_lat_ratio(lat1,lng1): 
    return lng1 / lat1

def lat_lng_ratio(lgn1, lgn2): 
    return lat1 / lgn1

4 两个经纬度的欧几里得距离计算

计算两个经纬度之间的欧几里得距离

def euclidean_distance(lat1, lng1, lat2, lng2): 
    return np.sqrt((lat1 - lat2) ** 2 + (lng1 - lng2) ** 2)

5 两个经纬度的Manhattan距离计算

计算两个经纬度之间的Manhattan距离

def manhattan_distance(lat1, lng1, lat2, lng2): 
    return abs(lat1 - lat2)  + abs(lng1 - lng2)

6 经纬度与斜边的比例特征

类似于三角形中两个直角边与斜边的比例信息

def lat_lng_hypotenuse_ratio(lat1, lng1): 
    hypotenuse = np.sqrt((lat1 ** 2 +  lng1 ** 2))
    return lat1 /  hypotenuse, lng1/  hypotenuse

7 基于经纬度的聚类1

基于经纬度进行聚类,将经纬度聚类的结果当做特征,例如常用的Kmeans。
此处我们用1表示,在第二部分我们会介绍升级版

from sklearn.cluster import MiniBatchKMeans
coords = np.vstack((train[['pickup_latitude', 'pickup_longitude']].values,
                    train[['dropoff_latitude', 'dropoff_longitude']].values,
                    test[['pickup_latitude', 'pickup_longitude']].values,
                    test[['dropoff_latitude', 'dropoff_longitude']].values))

sample_ind = np.random.permutation(len(coords))[:500000]
kmeans = MiniBatchKMeans(n_clusters=100, batch_size=10000).fit(coords[sample_ind])

train.loc[:, 'pickup_cluster'] = kmeans.predict(train[['pickup_latitude', 'pickup_longitude']])
train.loc[:, 'dropoff_cluster'] = kmeans.predict(train[['dropoff_latitude', 'dropoff_longitude']])
test.loc[:, 'pickup_cluster'] = kmeans.predict(test[['pickup_latitude', 'pickup_longitude']])
test.loc[:, 'dropoff_cluster'] = kmeans.predict(test[['dropoff_latitude', 'dropoff_longitude']])

7 基于经纬度的聚类2

前面的部分,我们说基于Kmeans,但很多专家更加倾向于加入其他的非线性聚类。
1.Perform some Hierarchical Clustering instead of KMeans because of KMeans workes along the maximizing variance if the feature space is linear in nature but if it is non-linear, then Hierarchical Clusterings like PAM, CLARA, and DBSCAN are best to use.

2.The choice of the clustering algorithm matters. I tested many algorithms like K-means, DBSCAN, and hierarchical clustering—the latter two seem to give better results when it comes to geospatial features.

from sklearn.cluster import KMeans ,AgglomerativeClustering

# creates 5 clusters using hierarchical clustering.
agc = AgglomerativeClustering(n_clusters =5, affinity='euclidean', linkage='ward')
train['pickup cluster'] = agc.fit_predict(train[['Pickup Lat','Pickup Long']])

# creates 5 clusters using k-means clustering algorithm.
kmeans = KMeans(5)
clusters = kmeans.fit_predict(train[['Pickup Lat','Pickup Long']])
train['pickup cluster'] = kmeans.predict(train[['Pickup Lat','Pickup Long']])

8 特殊经纬度信息

例如第一个出现的经纬度可能是出发地点,最后一个现实的经纬度是终点站,那么这两个就是非常重要的特殊经纬度

9 距离某些特殊地点的经纬度距离

例如距离地铁的距离,距离汽车站的距离(距离可以是Manhattan距离等等)

def manhattan_distance_tostation(lat1, lng1, st_lat, st_lng): 
    return abs(lat1 - st_lat)  + abs(lng1 - st_lng)

def euclidean_distance_tostation(lat1, lng1, st_lat, st_lng): 
    return np.sqrt((lat1 - st_lat) ** 2 + (lng1 - st_lng) ** 2)

10 两个经纬度Haversine距离计算

haversine公式确定了给定两个经纬度在球体上两点之间的 great-circle 距离, 在很多比赛中也是最常见到的一种特征

def haversine_array(lat1, lng1, lat2, lng2): 
    lat1, lng1, lat2, lng2 = map(np.radians, (lat1, lng1, lat2, lng2)) 
    AVG_EARTH_RADIUS = 6371 # in km 
    lat = lat2 - lat1 
    lng = lng2 - lng1 
    d = np.sin(lat * 0.5) ** 2 + np.cos(lat1) * np.cos(lat2) *      np.sin(lng * 0.5) ** 2 
    h = 2 * AVG_EARTH_RADIUS * np.arcsin(np.sqrt(d)) 
    return h

11 两个经纬度之间的Manhattan距离计算

沿直角轴测得的两点之间的距离

def dummy_manhattan_distance(lat1, lng1, lat2, lng2): 
    a = haversine_array(lat1, lng1, lat1, lng2) 
    b = haversine_array(lat1, lng1, lat2, lng1) 
    return a + b

12 两个经纬度之间的方位特征

表示两个经纬度之间的方位信息

def bearing_array(lat1, lng1, lat2, lng2): 
    AVG_EARTH_RADIUS = 6371 # in km 
    lng_delta_rad = np.radians(lng2 - lng1) 
    lat1, lng1, lat2, lng2 = map(np.radians, (lat1, lng1, lat2, lng2)) 
    y = np.sin(lng_delta_rad) * np.cos(lat2) 
    x = np.cos(lat1) * np.sin(lat2) - np.sin(lat1) * np.cos(lat2) * np.cos(lng_delta_rad) 
    return np.degrees(np.arctan2(y, x))

12 两个经纬度之间的Manhattan距离计算

沿直角轴测得的两点之间的距离

def dummy_manhattan_distance(lat1, lng1, lat2, lng2): 
    a = haversine_array(lat1, lng1, lat1, lng2) 
    b = haversine_array(lat1, lng1, lat2, lng1) 
    return a + b

13 两个经纬度之间的方位特征

表示两个经纬度之间的方位信息

def bearing_array(lat1, lng1, lat2, lng2): 
    AVG_EARTH_RADIUS = 6371 # in km 
    lng_delta_rad = np.radians(lng2 - lng1) 
    lat1, lng1, lat2, lng2 = map(np.radians, (lat1, lng1, lat2, lng2)) 
    y = np.sin(lng_delta_rad) * np.cos(lat2) 
    x = np.cos(lat1) * np.sin(lat2) - np.sin(lat1) * np.cos(lat2) * np.cos(lng_delta_rad) 
    return np.degrees(np.arctan2(y, x))

14 经纬度逆向编码

通过很多地图的api,将经纬度信息转换为详细地址信息,然后对这些地址进行编码

from pygeocoder import Geocoder
location = Geocoder.reverse_geocode(12.9716,77.5946)
print("City:",location.city)
print("Country:",location.country)

from geopy.geocoders import Nominatim
# create the locator
geolocator = Nominatim(user_agent="myGeocoder")
# getting the location address
location = geolocator.reverse("52.509669, 13.376294")
location.raw.get('address').get('state')
location.raw.get('address').get('city_district')
location.raw.get('address').get('country')
location.raw.get('address').get('postcode')

15 对经纬度进行其他转换

常见的是PCA转换(有些竞赛中说这种转换可以帮助树模型更好地分割)

pca = PCA().fit(coords)
train['pickup_pca0'] = pca.transform(train[['pickup_latitude', 'pickup_longitude']])[:, 0]
train['pickup_pca1'] = pca.transform(train[['pickup_latitude', 'pickup_longitude']])[:, 1]
train['dropoff_pca0'] = pca.transform(train[['dropoff_latitude', 'dropoff_longitude']])[:, 0]
train['dropoff_pca1'] = pca.transform(train[['dropoff_latitude', 'dropoff_longitude']])[:, 1]
test['pickup_pca0'] = pca.transform(test[['pickup_latitude', 'pickup_longitude']])[:, 0]
test['pickup_pca1'] = pca.transform(test[['pickup_latitude', 'pickup_longitude']])[:, 1]
test['dropoff_pca0'] = pca.transform(test[['dropoff_latitude', 'dropoff_longitude']])[:, 0]
test['dropoff_pca1'] = pca.transform(test[['dropoff_latitude', 'dropoff_longitude']])[:, 1]

16 距离某些特殊地点的经纬度距离

例如距离地铁的距离,距离汽车站的距离(距离计算换算成上面的Haversine等距离)
距离最近城市的距离
距离最近的最大的城市的距离
距离某些特殊站点(家,地铁…)的距离

17 经纬度的衍生编码等特征

例如距离地铁的距离,距离汽车站的距离(距离计算换算成上面的Haversine等距离)
距离最近的城市编码(人口数编码,城市编码等)
距离最近的最大的城市编码(人口数编码,城市编码等)等

参考:https://www.kesci.com/home/project/5e72091fc59d610036222d90

你可能感兴趣的:(python)