2011-08-24 19 views
11

tôi đã nhìn thấy trên SO và những nơi khác rằng đây là vụ phải làm việc (ví dụ này được nâng lên trực tiếp từ XSLT Cookbook O'Reilly):Làm thế nào để thực hiện thiết lập hoạt động trong XPath 1.0

(: intersection :) 
$set1[count(. | $set2) = count($set2)] 

(: difference :) 
$set1[count(. | $set2) != count($set2)] 

và nó có vẻ như nó sẽ là OK, tuy nhiên điều này dường như thất bại khi được sử dụng với đường dẫn thực tế chứ không phải là biến. Ví dụ, với các tài liệu sau đây

<a> 
    <new> 
    <val>1</val> 
    <val>2</val> 
    </new> 
    <old> 
    <val>2</val> 
    <val>3</val> 
    </old> 
</a> 

và biểu thức XPath /a/new/val[count(. | /a/old/val)=count(/a/old/val)]/text() tôi mong chờ để có được nút thiết lập { 2 } nhưng thay vào đó đang nhận được { 1 2 }. Bất kỳ ý tưởng những gì tôi đang làm sai?

+0

Câu hỏi hay, +1. Xem câu trả lời của tôi để giải thích về vấn đề của bạn và cho một biểu thức XPath một lớp đơn giản và dễ dàng - giải pháp - không có câu trả lời nào khác đề xuất một giải pháp vào lúc này. :) –

Trả lời

8

Các công thức cho nút giao điểm nút sử dụng nhận dạng nút, không phải là nhận dạng giá trị.

Hai nút là giống hệt nhau khi và chỉ khi count($n1|$n2) =1

Tuy nhiên, bạn muốn giao nhau dựa trên bản sắc giá trị.

Giải pháp:

Sử dụng:

/a/new/val[. = /a/old/val] 

này chọn bất kỳ /a/new/val mà tồn tại ít nhất một /a/old/val yếu tố như vậy mà giá trị chuỗi của hai yếu tố này là như nhau.

+0

Tuyệt vời - tại chỗ trên, hoạt động như một sự quyến rũ! –

+0

@Ian Phillips, Bạn được chào đón :) –

+0

Câu trả lời hay! Chúng ta có thể thực hiện các hoạt động * Minus * được không? –

1

Nhận xét giao lộ đó luôn dẫn đến một tập hợp nút đơn được tạo bởi các nút trong chung giữa hai nút gốc ban đầu.

Đồng thời lưu ý rằng hai nút có cùng tên và nội dung sẽ được coi là hai nút riêng biệt. Do đó /a/new/val/text()/a/old/val/text() có cùng giá trị nhưng chúng là các nút văn bản hoàn toàn khác biệt.

Như vậy ngã tư hiện tại của bạn:

/a/new/val[count(. | /a/old/val)=count(/a/old/val)] 

nên đánh giá một nút-tập rỗng, bởi vì bạn đang giao nhau hai nút-bộ mà không cần bất kỳ nút chung (count() hoạt động sẽ không bao giờ phù hợp). Bạn đang làm một việc như sau:

/a/new/val & # x2229; /a/old/val = & # x2205;

Trong khi /a/new & # x2229; /a/old/preceding::new sẽ sản xuất new.

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