Xcode 6 với tính năng nhập siêu chậm và tự động hoàn thành Swift


114

Có phải chỉ tôi hay Xcode 6 (6.0.1) với Swift dường như siêu chậm khi bạn nhập mã của mình, đặc biệt là với tính năng tự động hoàn thành?

Một lớp Objective-C bình thường, ngay cả khi bên trong một dự án Swift, hoạt động gần giống như trước, vì vậy Swift sẽ giết nó.

Có ai khác gặp phải sự bất tiện tương tự không? Bạn có bất kỳ ý tưởng nào về cách cải thiện hiệu suất không?

  • Tôi đã cố gắng chơi với một số cài đặt nhưng không may mắn.
  • Tất nhiên, tôi cũng đã thử khởi động lại Xcode và máy tính mà không gặp may.
  • Không có ứng dụng nặng nào khác đang mở.

Tôi sử dụng Macbook Pro giữa năm 2009 (Intel Core 2 Duo 2,26 GHz) với RAM 8GB và SSD HD, đây không phải là thứ mới nhất, nhưng vẫn chưa phải là thứ hoàn chỉnh.

Thật là tiếc vì tôi đã rất hào hứng khi bắt đầu sử dụng Swift và bây giờ nó thực sự không thể chịu đựng được.

Suy nghĩ / lời khuyên?


1
Tôi đang gặp vấn đề tương tự như bạn. Thường thì Xcode cho tôi biết "SourceKit đã bị chấm dứt, trình chỉnh sửa tạm thời bị giới hạn"
idmean

Vâng, đây cũng là một vấn đề khác, tôi không chắc chúng có liên quan với nhau. Nó chậm ngay cả khi lỗi đó đang xảy ra.
mllm

1
Tôi chắc rằng chúng có liên quan với nhau. Trong phiên bản beta 5, tôi thấy thông báo đó thường xuyên hơn và tôi thấy thông báo đó bất cứ lúc nào khi đề xuất không hoạt động. (Khi tôi gõ một số ký tự và nhấn Esc để kích hoạt các gợi ý)
idmean

1
Tôi có cùng một vấn đề. XCode của tôi sử dụng 300% + CPU và làm chậm võng mạc macbook của tôi xuống tốc độ nhanh. Những ngày này tôi khá mù quáng gõ và đợi xcode hoàn tất.
pkuhar

1
Gặp phải vấn đề tương tự với MacBook Pro 15,6 "cuối năm 2011 với RAM 8 GB và ổ SSD. 90% thời gian hoàn thành mã đóng băng Xcode, khi tôi kiểm tra màn hình hoạt động, tôi thấy mức sử dụng CPU ~ 200%. Thời gian đóng băng kéo dài sau vài giây đến một vài phút.
isair.

Câu trả lời:


86
  • Thoát Xcode và khởi động lại Mac là không bắt buộc nhưng được ưu tiên.
  • Xóa nội dung của thư mục ~ / Library / Developer / Xcode / DerivedData
  • Xóa nội dung ~ / Library / Caches / com.apple.dt.Xcode

Đây là một giải pháp tạm thời, nhưng có tác dụng rất lớn.

Bên dưới tập lệnh bằng ứng dụng Trình chỉnh sửa tập lệnh.

tell application "Terminal"
    do script "rm -frd ~/Library/Developer/Xcode/DerivedData/*"
    do script "rm -frd ~/Library/Caches/com.apple.dt.Xcode/*"
end tell

Ngoài ra, bạn có thể tạo bí danh cho thiết bị đầu cuối của mình như sau:

alias xcodeclean="rm -frd ~/Library/Developer/Xcode/DerivedData/* && rm -frd ~/Library/Caches/com.apple.dt.Xcode/*"

Bạn có thể thêm nó vào của bạn ~/.bash_profilevà sau đó gõ xcodecleanvào dòng lệnh mỗi khi bạn muốn xóa hai thư mục đó.


Chà, mặc dù nó không gần là hoàn hảo, nhưng có vẻ như giải pháp của bạn đã cải thiện đáng kể nó. Tôi sẽ đánh dấu là đang giải quyết, vì sau một thời gian dài, đây có lẽ là điều tốt nhất mà nó có thể nhận được. Sẽ rất vui khi biết về những người khác ... Cảm ơn rất nhiều!
mllm

Máy tính xách tay của tôi đã mất gần một phút để xóa tất cả nội dung khỏi hai thư mục đó. Việc lập chỉ mục trên Xcode hiện mất dưới 30 giây.
Eneko Alonso

Nó không giúp tôi nhập liệu và tự động hoàn thành nhanh hơn, nhưng nó đã giúp tôi giải phóng khá nhiều dung lượng khỏi máy Mac.
Scott Zhu

Câu trả lời này đã giúp ích cho điều tự động hoàn thành, stackoverflow.com/a/29849869/1213267
Scott Zhu

13

Tôi cũng gặp phải 100% + CPU trong khi gõ một số mã "đơn giản". Một số thủ thuật nhỏ để giúp phân tích cú pháp nhanh hơn bằng cách bạn cấu trúc mã của mình.

Không sử dụng ký tự "+" trong chuỗi. Đối với tôi, điều này gây ra sự chậm chạp rất nhanh chóng. Mỗi dấu "+" mới đưa trình phân tích cú pháp thu thập thông tin và nó phải phân tích lại mã mỗi khi bạn thêm một ký tự mới ở đâu đó trong thân hàm của mình.

Thay vì:

var str = "This" + String(myArray.count) + " is " + String(someVar)

Sử dụng cú pháp mẫu có vẻ hiệu quả hơn nhiều để phân tích cú pháp nhanh chóng:

var str = "This \(myArray.count) is \(someVar)"

Bằng cách này về cơ bản tôi không nhận thấy giới hạn trong strlen với các vars nội tuyến "\ (*)".

Nếu bạn có các phép tính sử dụng + / * - thì hãy chia chúng thành các phần nhỏ hơn.

Thay vì:

var result = pi * 2 * radius 

sử dụng:

var result  = pi * 2
    result *= radius

Nó có thể trông kém hiệu quả hơn, nhưng trình phân tích cú pháp nhanh hơn theo cách này nhanh hơn nhiều. Một số công thức sẽ không biên dịch, nếu chúng phải thực hiện nhiều phép toán, ngay cả khi chúng đúng về mặt toán học.

Nếu bạn có một số phép tính phức tạp thì hãy đặt nó trong một func. Bằng cách này, trình phân tích cú pháp có thể phân tích cú pháp một lần và không phải phân tích lại nó mỗi khi bạn thay đổi điều gì đó trong cơ thể hàm của mình.

Bởi vì nếu bạn có một phép tính trong phần thân hàm của mình thì bằng cách nào đó, trình phân tích cú pháp nhanh sẽ kiểm tra nó mọi lúc nếu các kiểu, cú pháp, v.v. vẫn đúng. Nếu một dòng thay đổi phía trên phép tính, thì một số dòng bên trong phép tính / công thức của bạn có thể đã thay đổi. Nếu bạn đặt nó vào một chức năng bên ngoài thì nó sẽ được xác thực một lần và nhanh chóng rất vui vì nó sẽ đúng và không phải trả lại liên tục, điều này gây ra việc sử dụng CPU cao.

Bằng cách này, tôi đã nhận được từ 100% trên mỗi lần nhấn phím đến CPU thấp trong khi nhập. Ví dụ: 3 dòng này được đặt nội tuyến trong phần thân hàm của bạn có thể đưa người chạy nhanh hơn đến thu thập thông tin.

let fullPath =  "\(NSHomeDirectory())/Library/Preferences/com.apple.spaces.plist"
let spacesData  = NSDictionary(contentsOfFile: fullPath )! // as Dictionary<String, AnyObject>
let spaces : AnyObject   = spacesData["SpacesDisplayConfiguration"]!["Management Data"]!!["Monitors"]!![0]["Spaces"]!! 

println ( spaces )

nhưng nếu tôi đặt nó trong một func và gọi nó sau, swiftparser sẽ nhanh hơn nhiều

// some crazy typecasting here to silence the parser
// Autodetect of Type from Plist is very rudimentary, 
// so you have to teach swift your types
// i hope this will get improved in swift in future
// would be much easier if one had a xpath filter with
// spacesData.getxpath( "SpacesDisplayConfiguration/Management Data/Monitors/0/Spaces" ) as Array<*> 
// and xcode could detect type from the plist automatically
// maybe somebody can show me a more efficient way to do it
// again to make it nice for the swift parser, many vars and small statements
func getSpacesDataFromPlist() -> Array<Dictionary<String, AnyObject>> {
  let fullPath =  "\(NSHomeDirectory())/Library/Preferences/com.apple.spaces.plist"

  let spacesData  = NSDictionary(contentsOfFile: fullPath )!    as Dictionary<String, AnyObject>
  let sdconfig    = spacesData["SpacesDisplayConfiguration"]    as Dictionary<String, AnyObject>
  let mandata     = sdconfig["Management Data"]                 as Dictionary<String, AnyObject> 
  let monitors    = mandata["Monitors"]                         as Array<Dictionary<String, AnyObject>> 
  let monitor     = monitors[0]                                 as Dictionary<String, AnyObject>
  let spaces      = monitor["Spaces"]                           as Array<Dictionary<String, AnyObject>>

  return spaces
}

func awakeFromNib() {
  ....
  ... typing here ...

  let spaces = self.getSpacesDataFromPlist()
  println( spaces) 
}

Swift và XCode 6.1 vẫn còn rất nhiều lỗi, nhưng nếu bạn làm theo các thủ thuật đơn giản này, việc chỉnh sửa mã trở nên có thể chấp nhận được. Tôi thích nhanh hơn rất nhiều, vì nó loại bỏ các tệp .h và sử dụng cú pháp gọn gàng hơn nhiều. Vẫn còn nhiều kiểu ép kiểu cần thiết như "myVar as AnyObject", nhưng đó là cái ác nhỏ hơn so với cấu trúc và cú pháp dự án target-c phức tạp.

Ngoài ra, một trải nghiệm khác, tôi đã thử SpriteKit, nó rất thú vị khi sử dụng, nhưng nó khá kém hiệu quả nếu bạn không cần sơn lại liên tục ở tốc độ 60 khung hình / giây. Sử dụng CALayers cũ sẽ tốt hơn nhiều cho CPU nếu "sprites" của bạn không thay đổi thường xuyên. Nếu bạn không thay đổi .contents của các lớp thì CPU về cơ bản không hoạt động, nhưng nếu bạn có ứng dụng SpriteKit đang chạy trong nền, thì video phát lại trong các ứng dụng khác có thể bắt đầu bị giật do vòng lặp cập nhật 60 khung hình / giây không giới hạn.

Đôi khi xcode hiển thị các lỗi kỳ lạ trong khi biên dịch, sau đó vào menu "Sản phẩm> Dọn dẹp" và biên dịch lại, có vẻ như là một lỗi triển khai bộ nhớ cache.

Một cách tuyệt vời khác để cải thiện phân tích cú pháp khi xcode bị kẹt với mã của bạn được đề cập trong một bài đăng stackoverflow khác tại đây . Về cơ bản, bạn sao chép tất cả nội dung từ tệp .swift của mình vào một trình chỉnh sửa bên ngoài, sau đó hoạt động theo chức năng, sao chép lại và xem điểm nghẽn của bạn ở đâu. Điều này thực sự đã giúp tôi lấy lại xcode với tốc độ hợp lý, sau khi dự án của tôi trở nên điên rồ với 100% CPU. trong khi sao chép lại mã của bạn, bạn có thể cấu trúc lại nó và cố gắng giữ cho phần thân hàm của bạn ngắn gọn và các hàm / công thức / biểu thức đơn giản (hoặc chia thành nhiều dòng).


Câu trả lời rất tường tận. Có thể một số gợi ý tuyệt vời như "sơ cứu", nhưng thực sự, chúng ta không mong đợi Xcode có thể hoạt động đơn giản mà không gặp phải rắc rối lớn nào?
mllm

1
tiếc là xcode 6.1 + swift khá không ổn định, vì vậy cần phải có những "bản hack" này. Apple nên sửa lỗi swift và xcode. Nhưng swift rất hay để lập trình, vì vậy trong ngắn hạn đây là cách duy nhất để giữ cho CPU-Usage ở mức thấp.
Daniel Unterberger

Tôi đã thực hiện tất cả các thay đổi có thể mà bạn đề xuất nhưng không may là quá trình tự động hoàn thành của tôi vẫn tệ. Tôi nghi ngờ rằng cách viết tắt if mệnh đề cũng có thể gây rắc rối. Ý tôi là return (a == b)? x: y
Ilker Baltaci

Vâng, viết code theo một cách nào đó để làm cho IDE hạnh phúc là một điều vô nghĩa thực
Andrey Gordeev

10

Tự động điền đã bị hỏng kể từ Xcode 4. Cho đến khi Apple quyết định sửa lỗi 2 năm tuổi này, giải pháp duy nhất, thật không may, là TẮT hoàn thành mã theo tùy chọn của XCode (tùy chọn đầu tiên của hình bên dưới).

Bạn có thể tiếp tục hoàn thành theo cách thủ công bằng cách nhập CTRL spacehoặc ESCkhi bạn cần.

Đây là giải pháp duy nhất hoạt động mọi lúc cho 100% trường hợp.

nhập mô tả hình ảnh ở đây

Một điều khác mà tôi đã phát hiện ra gần đây là: nếu bạn sử dụng plugin trên Xcode thì không. Loại bỏ tất cả chúng. Chúng làm cho vấn đề trở nên tồi tệ hơn.


5

Bạn đang sử dụng Spotify? Tôi đã cài đặt Yosemite GM với Xcode 6.1 GM trên iMac giữa năm 2009 (2,66Ghz) gặp vấn đề tương tự. Tôi nhận thấy rằng một quy trình có tên "SpotifyWebHelper" luôn được đánh dấu màu đỏ là không phản hồi, vì vậy tôi đã tắt tùy chọn "bắt đầu từ web" trong spotify và bây giờ Xcode dường như chạy tốt hơn đáng kể.


Thật thú vị, nhưng đối với tôi, nó không liên quan đến Spotify ... Tuy nhiên, nó cho thấy có thể đó chỉ là một vấn đề hiệu suất "thông thường" - nghĩa là - xóa nhiều tài nguyên hơn và nó sẽ hoạt động tốt hơn. Điều đó thật đáng buồn vì tôi không còn tài nguyên nào để cung cấp (ngoài tiền trên máy mac mới).
mllm

2

Tôi phát hiện ra rằng điều đó thường xảy ra khi bạn:

  • có các biểu thức dài trong một câu lệnh duy nhất (xem câu trả lời này )
  • trộn nhiều toán tử tùy chỉnh trong một biểu thức duy nhất

Trường hợp thứ hai dường như đã được khắc phục trong một trong những bản phát hành xcode mới nhất. Ví dụ: Tôi đã xác định 2 toán tử tùy chỉnh <&&> và <||> và được sử dụng trong một biểu thức như a <&&> b <&&> c <||> d. Việc chia thành nhiều dòng đã giải quyết được vấn đề:

let r1 = a <&&> b
let r2 = r1 <&&> c
let r3 = r2 <||> d

Tôi hy vọng rằng trường hợp của bạn thuộc một trong 2 trường hợp trên ... vui lòng gửi bình luận một trong hai trường hợp


5
Thật không may, nó cũng xảy ra trong một dự án hoàn toàn mới mà không có gì trong đó và với việc gõ một cái gì đó đơn giản như "var s: Stri ...". Ngay sau khi tôi bắt đầu nhập St ... nó sẽ chậm khi tra cứu các đề xuất hoàn thành.
mllm

Nó chắc chắn là toán hạng đối với tôi. Có nhiều hơn một toán hạng trong cùng một dòng gây ra điều đó. Cảm ơn vì câu trả lời. Đây phải là câu trả lời đúng
Kesava

2

Tôi đã gặp vấn đề tương tự ngay cả trong Xcode 6.3

  • tự động hoàn thành siêu chậm
  • lập chỉ mục siêu chậm
  • sử dụng CPU rất lớn nhờ nhanh chóng và SourceKitService
  • sử dụng bộ nhớ lớn của SourceKitService

Tất cả điều này đã xảy ra ngay cả trong một dự án tương đối nhỏ. Tôi đã thử tất cả các bản sửa lỗi mà tôi có thể tìm thấy:

  • xóa ~ / Library / Developer / Xcode / DerivedData / *
  • xóa ~ / Library / Caches / com.apple.dt.Xcode / *
  • xóa tất cả chuỗi "+" kết hợp khỏi mã
  • đã xóa tất cả các khai báo từ điển đáng ngờ

Không ai trong số này thực sự giúp ích cho dự án của tôi.

Điều thực sự giải quyết được vấn đề của tôi là:

  • đặt mỗi đầu mỗi lớp trong tệp riêng của nó
  • đặt mỗi và mọi phần mở rộng trong tệp riêng của nó (Class + ExtName.swift)
  • đặt "các phương thức nhanh ngoài lớp" trong tệp riêng của nó

Bây giờ tôi gần như không sử dụng CPU, sử dụng bộ nhớ thấp và hoàn thành rất nhanh.


2

Nói chung, việc di chuyển thư mục bộ nhớ cache (DerivedData) sang ổ SSD (cụ thể là trong trường hợp của tôi - một bộ nhớ ngoài được kết nối với lối ra Thunderbolt) đã cải thiện đáng kể hiệu suất Xcode của tôi. Thời gian biên dịch và thắc mắc chung quanh ứng dụng nhanh hơn khoảng 10 lần .. Đồng thời chuyển toàn bộ thư mục git sang SSD, điều này đã cải thiện đáng kể hiệu suất git.


Trên thực tế, trong vấn đề ban đầu, tôi đã nâng cấp máy mac của mình với ổ SSD và mọi thứ đều chạy từ nó. hệ điều hành và vẫn có vấn đề
mllm

2

Đó là một nỗi đau cho đến khi XCode 7.2.

Apple đã sửa nó trong XCode 7.3 và bây giờ nó hoạt động như một sự quyến rũ. Nó siêu nhanh và mạnh hơn nhiều vì nó có vẻ hoạt động giống như tìm kiếm tệp mờ: bạn không phải thực sự nhập chính xác phần đầu của phương thức / thuộc tính để nó xuất hiện trong danh sách mệnh đề.


2

Thu gọn tất cả các phương pháp giúp một chút.

Command-alt-shift-mũi tên trái sẽ thực hiện thủ thuật ...

Để gấp / mở các phương thức hiện tại hoặc nếu các cấu trúc sử dụng:

Gấp: command-alt-mũi tên trái

Mở ra: command-alt-mũi tên phải


1

SourceKitServicecũng khá vụng về khi xử lý các nhận xét trong mã và các nhận xét được nhúng cũng làm chậm nó.

vì vậy nếu bạn có đủ khả năng để loại bỏ khối lượng lớn các nhận xét được nhúng như thế này:

/*
 * comment 
    /*
     * embedded comment
     */
 */

điều đó chắc chắn cũng có thể hữu ích.


LƯU Ý: trong trường hợp của tôi, Xcode 7.3.1 (7D1014) của tôi đã thực sự chặn tôi nhập bất kỳ ký tự nào khi tệp có khoảng 700 dòng nhận xét với các nhận xét được nhúng. ban đầu tôi đã xóa khối đó khỏi .swifttệp đó và Xcode đã hoạt động trở lại. Tôi đã thử thêm lại từng phần nhận xét của mình bằng cách xóa các nhận xét được nhúng, tốc độ vẫn chậm hơn bình thường nhưng nó cho thấy hiệu suất tốt hơn đáng kể nếu không có nhận xét được nhúng.


1

Tôi đã gặp vấn đề tương tự khi nhập bị chậm trong một lớp cụ thể và hóa ra là

/* Long multiline comments */

đang làm chậm quá trình đánh máy.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.