2010-09-26 36 views
32

Tôi đang cố gắng lưu một vị trí và truy xuất vị trí trên bản đồ sau đó sử dụng các vị trí lõi, MapKit và Core Data.Làm thế nào để lưu trữ CLLocation bằng cách sử dụng dữ liệu lõi (iPhone)?

Điều tôi đã làm là tôi vừa tạo thực thể có tên là POI và thêm các thuộc tính như vĩ độ (loại kép), kinh độ (loại kép) với vài loại khác.

Nói một cách đơn giản, ứng dụng của tôi sẽ lưu POI với hai NSNumbers. (lat và dài) nhưng tôi cảm thấy như phải có một cách thông minh hơn để lưu trữ CLLocation hơn thế.

cổ vũ.

Trả lời

34

Điều bạn đang làm là tốt. Bạn nên lưu vĩ độ và kinh độ làm tăng gấp đôi trong Dữ liệu cốt lõi. Khi bạn cần lấy lại thông tin, hãy lấy lại dữ liệu từ Core Data và xây dựng một cấu trúc CLLocationCoordinate2D với chức năng như CLLocationCoordinate2DMake. Không có cách nào được xây dựng để lưu trữ một vị trí, vì vậy việc lưu trữ các thành phần vĩ độ và kinh độ là tốt.

Nếu bạn không thực hiện bất kỳ phép toán nào trên vĩ độ hoặc kinh độ (tìm các hộp giới hạn vv), bạn có thể lưu trữ chúng dưới dạng chuỗi. Nổi và đôi có thể thay đổi giá trị của chúng một chút, khiến cho các hoạt động so sánh thất bại.

+0

Cảm ơn nevan, thực sự tôi đã lưu các giá trị tọa độ đó trong NSString cũng như hiển thị trong UILabel. Tôi có kế hoạch để làm một số toán học với tọa độ nhưng tôi không biết rằng "Nổi và đôi có thể thay đổi giá trị của họ một chút, làm cho các hoạt động so sánh thất bại." điều đó khiến tôi quay lại câu hỏi ban đầu với sự thay đổi nhỏ; Nếu bạn cần tính toán khoảng cách và so sánh, cách tốt nhất để lưu trữ các giá trị tọa độ CLLocation bằng cách sử dụng Dữ liệu lõi là gì? – bicbac

+2

Nếu bạn đang thực hiện một số tính toán trên chúng, như tìm tất cả các vĩ độ lớn hơn 12,34, tôi sẽ lưu trữ chúng dưới dạng phao hoặc tăng gấp đôi. Chỉ cần không dựa vào giá trị float là chính xác như nhau giữa lưu trữ nó và lấy nó. Nếu bạn muốn đảm bảo giá trị không thay đổi (thậm chí là một phần nhỏ), hãy sử dụng số thập phân. Tôi không chắc là làm toán với các loại thập phân nhanh như thế nào. Đây là một liên kết: http://stackoverflow.com/questions/159255/what-is-the-ideal-data-type-to-use-when-storing-latitude-longitudes-in-a-mysql/159333#159333 –

+2

Nếu bạn cần lưu trữ các giá trị số với độ chính xác cao và thực hiện các thao tác trên chúng, bạn nên sử dụng số NSD. Sử dụng biến áp giá trị để lưu trữ chúng trong Dữ liệu chính. Tuy nhiên, tôi nghĩ rằng đó sẽ là quá mức cần thiết trong trường hợp này. Nổi và đôi có thể thay đổi giá trị nhưng chỉ ở mức cực kỳ chính xác. Vĩ độ/Kinh độ chỉ yêu cầu tối đa 4 chữ số thập phân ở bên phải để bạn có thể chỉ cần kiểm soát các chữ số quan trọng của mình để lưu trữ và truy xuất các giá trị đó bằng phao. – TechZen

26

CLLocation triển khai giao thức NSCoding để bạn có thể lưu trữ chúng trong Dữ liệu cốt lõi dưới dạng thuộc tính có thể chuyển đổi. Bạn có thể sử dụng biến mặc định NSKeyedUnarchiveFromData.

Bạn chỉ cần chuyển đối tượng CCLocation vào thuộc tính đối tượng được quản lý và nó sẽ tuần tự hóa nó thành dữ liệu và lưu trữ nó dưới dạng blob trong cửa hàng SQL. Khi bạn cần đối tượng vị trí, nó sẽ tự động đảo ngược tiến trình và trả về cho bạn một đối tượng CCLocation được điền đầy đủ.

Đó có thể là cách dễ nhất để có được những gì bạn muốn.

+14

Nếu dữ liệu được đăng theo thứ tự, bạn sẽ không thể lấy các vị trí trong một hộp giới hạn mà không tìm nạp mọi vị trí từ cửa hàng. –

+0

có thể dễ dàng nhưng không thể truy vấn khi được lưu trữ ở định dạng đó. – malhal

17

Các "tốt nhất" cách để lưu trữ nó phụ thuộc vào những gì bạn muốn làm gì với nó:

  • Nếu bạn muốn "giống nhau" CLLocation, serialize nó. NSKeyedUnarchiveFromData là tốt.
  • Nếu bạn chỉ muốn tìm kiếm trên vĩ độ và kinh độ, hãy lưu trữ những vị trí đó làm tăng gấp đôi (và chọn hộp kiểm "được lập chỉ mục").

Có một loạt thuộc tính bổ sung mà bạn có thể lưu/khôi phục nếu bạn thực hiện thủ công (độ cao, ngangAccuracy, verticalAccuracy, dấu thời gian). Có một số chi tiết mà bạn không thể (tốc độ, tiêu đề); CLLocation không cung cấp phương thức init thích hợp và các thuộc tính là chỉ đọc.

Tất cả thuộc tính bổ sung đều hữu ích nếu bạn đang ghi tuyến đường. Độ cao hữu ích nếu bạn đang ghi lại POI trên địa hình miền núi ("chúng tôi vẫn phải leo lên 100 m"). độ chính xác ngang/dọc có thể được sử dụng để đại diện cho POI lớn như thế nào (ví dụ: thành phố có thể có "độ chính xác ngang" vài km và được hiển thị dưới dạng vòng tròn lớn).

2

Bạn có thể thực hiện việc này rất đơn giản chỉ bằng cách đặt loại thuộc tính Dữ liệu cốt lõi thành Transformable. Biến áp mặc định nếu bạn để trống Tên biến áp giá trị trống là NSKeyedArchiver hoạt động với hầu hết các loại Foundation như NSURL và CLLocation.

0

Bạn không cần phải sử dụng NSNumber để lưu trữ các điểm kinh độ và vĩ độ. Bạn có thể lưu trữ CLLocation trực tiếp vào dữ liệu lõi thay vào đó.

Thiết lập thực thể cho từng CLLocation, nó sẽ là quá nhiều quan hệ với bất kỳ thực thể nào đang sử dụng các điểm vị trí. Hãy gọi LocationPoint này:

class LocationPoint: NSManagedObject { 

@NSManaged var game: NSNumber 
@NSManaged var time: NSDate 
@NSManaged var location: AnyObject 

} 

Sau đó bạn thiết lập các vị trí tài sản cho năng biến trong mô hình dữ liệu Xcode. Đó là nó!

Trong Objective-C, bạn có thể thực sự vẫn phải kê khai tài sản LocationPoint này như CLLocation mà không cần bất kỳ lỗi:

@property (nonatomic, strong) CLLocation *location 

More info here.

Các vấn đề liên quan