Phá vỡ khi giá trị thay đổi bằng trình gỡ lỗi Visual Studio


198

Có cách nào để đặt đồng hồ trên biến và chỉ có Visual Studio nghỉ khi giá trị đó thay đổi?

Nó sẽ làm cho nó dễ dàng hơn nhiều để tìm thấy các vấn đề nhà nước khó khăn.

Điều này có thể được thực hiện?

Các điều kiện điểm dừng vẫn cần một bộ điểm dừng và tôi muốn đặt một chiếc đồng hồ và để Visual Studio đặt các điểm dừng ở các thay đổi trạng thái.


nhưng điểm dừng không ảnh hưởng đến bất cứ điều gì trừ khi điều kiện giữ, vì vậy bạn có thể đặt điểm dừng của mình ở bất cứ đâu (như Setter) và lấy nó từ đó. Hay tôi đang thiếu một cái gì đó?
Oskar

6
tốt. Nó giống như cách gỡ lỗi vb6. bạn không quan tâm đến vị trí điểm dừng. chỉ cần thêm một biểu thức có điều kiện vào cửa sổ xem và vb6 sẽ đảm bảo nó sẽ phá vỡ bất cứ khi nào điều kiện được đáp ứng ..
Gulzar Nazim

xin lỗi, chưa bao giờ thấy một con đường, theo như tôi biết thì setter là con đường để đi
Oskar

1
tôi đã hy vọng tìm thấy tin tức tốt hơn; các VS2010 chỉ ra không thay đổi msdn.microsoft.com/en-us/library/350dyxd0.aspx chỉ mẹ đẻ c ++ đã @Scottgu này bạn có thể làm tốt hơn!
gerryLowry

Câu trả lời:


134

Trong menu Visual Studio 2005:

Gỡ lỗi -> Điểm dừng mới -> Điểm dừng dữ liệu mới

Đi vào:

&myVariable

38
cái này có sẵn cho mã được quản lý không? Tôi thấy tùy chọn này bị vô hiệu hóa cho dự án C #. Hãy nhớ đọc ở đâu đó đây là một tính năng khó thực hiện trong việc gỡ lỗi các ứng dụng được quản lý, đặc biệt là với trình thu gom rác có liên quan.
Gulzar Nazim

27
Đó là chỉ có sẵn cho unmanaged code, không may: msdn.microsoft.com/en-us/library/350dyxd0.aspx
Josh Kodroff

17
Bạn cũng có thể tạm thời chuyển đổi một trường thành một thuộc tính và đặt một điểm dừng trên getter hoặc setter.
Jon Davis

12
Tùy chọn "Điểm dừng dữ liệu" trong "Gỡ lỗi -> Điểm dừng mới" bị vô hiệu hóa .. bạn có biết tại sao không? Nó vẫn bị vô hiệu hóa hay không tôi thực sự gỡ lỗi hay không. Tôi đang sử dụng Visual Studio 2015.
jbb 8/11/2016

2
Hơi muộn một chút nhưng @jbb đối với tôi nó chỉ được kích hoạt khi tôi dừng ở điểm dừng trong khi gỡ lỗi.
Allball103

27

Bạn cũng có thể chọn ngắt rõ ràng trong mã:

// Assuming C#
if (condition)
{
    System.Diagnostics.Debugger.Break();
}

Từ MSDN:

Trình gỡ lỗi.Break: Nếu không có trình gỡ lỗi nào được đính kèm, người dùng sẽ được hỏi liệu họ có muốn đính kèm trình gỡ lỗi không. Nếu có, trình gỡ lỗi được bắt đầu. Nếu trình gỡ lỗi được đính kèm, trình gỡ lỗi được báo hiệu với sự kiện điểm dừng của người dùng và trình gỡ lỗi tạm dừng thực thi quy trình giống như điểm dừng của trình gỡ lỗi đã bị tấn công.

Đây chỉ là một dự phòng. Đặt điểm dừng có điều kiện trong Visual Studio, như được mô tả trong các nhận xét khác, là lựa chọn tốt hơn.


2
FWIW, với chỉnh sửa và tiếp tục, tôi thích làm theo cách này: IME, các điểm dừng có điều kiện là sloooow
Mark Sowul

Điều này hoạt động - nhưng nó rất đau đớn - cuối cùng tôi đã làm một điều tương tự - tôi đặt nó ở đầu mọi phương pháp mà tôi nghi ngờ - và một lần nữa ở phía dưới (trong một mệnh đề cuối cùng) - theo cách đó tôi biết chính xác phương pháp đã gây ra sự cố - (tức là tôi biết dữ liệu là tốt trước khi nhập phương thức, và sau đó xấu trước khi thoát khỏi nó).
BrainSlugs83

26

Bài viết thực sự cũ nhưng trong trường hợp ai đó không biết ...

Trong Visual Studio 2015 , bạn có thể đặt một điểm dừng trên trình truy cập setcủa Thuộc tính được triển khai tự động và trình gỡ lỗi sẽ bị hỏng khi thuộc tính được cập nhật

public bool IsUpdated
{
    get;
    set;    //set breakpoint on this line
}

Cập nhật

Cách khác; @AbdulRaufMujahid đã chỉ ra trong các nhận xét rằng nếu thuộc tính được triển khai tự động nằm trên một dòng, bạn có thể đặt con trỏ của mình tại get;hoặc set;và nhấn F9và điểm dừng sẽ được đặt tương ứng. Đẹp!

public bool IsUpdated { get; set; }

5
Ngay cả khi thuộc tính được triển khai tự động nằm trong một dòng, ví dụ chuỗi công khai UserName {set; được; }. Người dùng có thể đánh dấu getter hoặc setter và có thể nhấn F9 để thêm điểm dừng
Abdul Rauf

@AbdulRaufMujahid Tuyệt vời!
Craig

13

Hãy tưởng tượng bạn có một lớp gọi là A với khai báo sau.

class A  
{  
    public:  
        A();

    private:
        int m_value;
};

Bạn muốn chương trình dừng lại khi ai đó sửa đổi giá trị của "m_value".

Đi đến định nghĩa lớp và đặt một điểm dừng trong hàm tạo của A.

A::A()
{
    ... // set breakpoint here
}

Khi chúng tôi dừng chương trình:

Gỡ lỗi -> Điểm dừng mới -> Điểm dừng dữ liệu mới ...

Địa chỉ: & (this-> m_value)
Byte Count: 4 (Vì int có 4 byte)

Bây giờ, chúng tôi có thể tiếp tục chương trình. Trình gỡ lỗi sẽ dừng khi giá trị được thay đổi.

Bạn có thể làm tương tự với các lớp kế thừa hoặc các lớp ghép.

class B
{
   private:
       A m_a;
};

Địa chỉ: & (này-> m_a.m_value)

Nếu bạn không biết số byte của biến bạn muốn kiểm tra, bạn có thể sử dụng toán tử sizeof.

Ví dụ:

// to know the size of the word processor,  
// if you want to inspect a pointer.
int wordTam = sizeof (void* ); 

Nếu bạn nhìn vào "Ngăn xếp cuộc gọi", bạn có thể thấy hàm đã thay đổi giá trị của biến.


1
Vậy, chính xác thì bạn sẽ làm gì nếu thứ tôi đang tìm kiếm không có trong lớp học của riêng tôi? Ví dụ như, tôi đang cố gắng tìm hiểu chính xác nơi điều khiển được bật hoặc tắt? Tôi có thể thêm một chiếc đồng hồ vào giá trị Kích hoạt của điều khiển trong quá trình gỡ lỗi, chắc chắn, nhưng không có cách nào để làm cho nó bị hỏng khi thay đổi và sau đó nhìn vào nơi nó dừng lại.
Nyerguds

2
Nếu bạn cố gắng gỡ lỗi một thư viện bên ngoài, bạn sẽ cần thư viện được biên dịch ở chế độ gỡ lỗi. Tôi không quen thuộc với thành phần, nhưng có lẽ bạn có thể kết nối "gọi lại" với tài sản và đặt một điểm dừng bên trong. Các hình thức mà tôi mô tả cần địa chỉ bộ nhớ, nếu bạn không có cách nào để biết nó, đó là tìm kiếm các phương pháp khác.
momboco

9

Thay đổi biến thành thuộc tính và thêm điểm dừng trong phương thức đặt. Thí dụ:

private bool m_Var = false;
protected bool var
{
    get { 
        return m_var;
    }

    set { 
        m_var = value;
    }
}

3

Nếu bạn đang sử dụng WPF, có một công cụ tuyệt vời: WPF Inspector .
Nó tự gắn vào ứng dụng WPF và hiển thị toàn bộ cây điều khiển với tất cả các thuộc tính, nó cho phép bạn (trong số những thứ khác) phá vỡ mọi thay đổi thuộc tính.

Nhưng buồn thay, tôi đã không tìm thấy bất kỳ công cụ nào cho phép bạn làm điều tương tự với BẤT K property thuộc tính hoặc biến nào.



2

Nhấp chuột phải vào điểm dừng hoạt động tốt đối với tôi (mặc dù chủ yếu tôi đang sử dụng nó cho các điểm dừng có điều kiện trên các giá trị biến cụ thể. Ngay cả việc ngắt các biểu thức liên quan đến tên luồng cũng rất hữu ích nếu bạn đang cố gắng phát hiện các vấn đề luồng).


2

Như Peter Mortensen đã viết:

Trong menu Visual Studio 2005:

Gỡ lỗi -> Điểm dừng mới -> Điểm dừng dữ liệu mới

Nhập: & myVariable

Thông tin thêm:

Rõ ràng, hệ thống phải biết địa chỉ nào trong bộ nhớ để xem. Vì vậy - đặt điểm dừng bình thường thành khởi tạo myVariable(hoặc myClass.m_Variable) - chạy hệ thống và đợi cho đến khi nó dừng tại điểm dừng đó. - Bây giờ, mục nhập Menu được bật và bạn có thể xem biến bằng cách nhập &myVariablehoặc thể hiện bằng cách nhập &myClass.m_Variable. Bây giờ các địa chỉ được xác định rõ.

Xin lỗi khi tôi đã làm những điều sai trái bằng cách giải thích một giải pháp đã được đưa ra. Nhưng tôi không thể thêm một bình luận, và đã có một số bình luận liên quan đến điều này.


1

Bạn có thể sử dụng một điểm theo dõi bộ nhớ trong mã không được quản lý. Không chắc chắn nếu những điều này có sẵn trong mã được quản lý mặc dù.


1

Bạn có thể có thể sử dụng thông minh hàm DebugBreak () .


Thật là chính xác? Bằng cách chạy một luồng riêng biệt trong một vòng lặp chặt chẽ và gọi DebugBreak () bất cứ khi nào có thay đổi?
nalply

@nalpy Ví dụ, bạn có thể theo dõi các vị trí myVariableđược sử dụng và lưu trữ các giá trị của nó sau khi sử dụng trong một previousValuebiến phụ , sau đó gọi DebugBreak () khi myVariable!=previousValue; sau đó bạn sẽ biết giữa các khối mã myVariableđã thay đổi. Nhưng tôi đồng ý rằng giải pháp của AShelly là tốt nhất.
lau

1

Bạn có thể tùy chọn quá tải toán tử = cho biến và có thể đặt điểm dừng bên trong hàm bị quá tải vào điều kiện cụ thể.


1

Cập nhật năm 2019:

Điều này hiện được hỗ trợ chính thức trong Visual Studio 2019 Preview 2 cho .Net Core 3.0 trở lên. Tất nhiên, bạn có thể phải đặt một số suy nghĩ về những rủi ro tiềm ẩn khi sử dụng phiên bản Preview của IDE. Tôi tưởng tượng trong tương lai gần, điều này sẽ được đưa vào Visual Studio chính thức.

https://bloss.msdn.microsoft.com/visualstudio/2019/02/12/break-when-value-changes-data-breakpoint-for-net-core-in-visual-studio-2019/

May mắn thay, các điểm dừng dữ liệu không còn là độc quyền của C ++ vì giờ đây chúng đã có sẵn cho .NET Core (3.0 trở lên) trong Visual Studio 2019 Preview 2!

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.