गणितज्ञ 745 681 बाइट्स
मूल विचार संभव चालों का भारित ग्राफ बनाना है। वजन एक स्थान से दूसरे स्थान तक जाने में लगने वाला समय है। कम से कम वजन वाला रास्ता सबसे तेज होगा।
इनपुट अंकों को आर (सी द्वारा कॉलम) पंक्तियों में आयताकार सरणी में रखा जाता है और फिर तीन अलग-अलग अभ्यावेदन आते हैं: (1) सी ग्रिड ग्राफ द्वारा एक आर, जहां प्रत्येक शीर्ष सरणी में एक सेल से मेल खाती है, (2) (r c) द्वारा (r c) भारित आसन्न मैट्रिक्स, जो उस समय (2, 3, या 11 मिनट) के बराबर वजन रखती है, एक स्थान से दूसरे स्थान पर जाने के लिए (ग्रिड ग्राफ में) दूसरे में, और (3) एक निर्देशित , मैट्रिक्स से निर्मित भारित आसन्न ग्राफ।
ग्रिड ग्राफ यह निर्धारित करने में मदद करता है कि कौन सी कोशिकाएं (अर्थात कौन सी कोने) संभवतः प्रत्येक शीर्ष से पहुंच योग्य हैं - "संभवतः पहुंच योग्य" क्योंकि एक पड़ोसी सेल को किसी दिए गए सेल के ऊपर, दाएं, बाएं या ऊपर नहीं होना चाहिए। यह मान भी पड़ोसी से दूरी की 1 इकाई के भीतर होना चाहिए (जैसे, 3 पड़ोसी 5 या 1 से कनेक्ट नहीं होता है)। यदि वर्टेक्स वर्टेक्स a
से जुड़ा नहीं है, b
तो आसन्न मैट्रिक्स सेल {a, b} और {b, a} का मान होगा। तदनुसार, भारित आसन्न ग्राफ में a से b तक की बढ़त नहीं होगी, न ही b से a तक।
भारित आसन्न ग्राफ GraphDistance
किसी भी कोने के बीच न्यूनतम दूरी ( ) और सबसे छोटा मार्ग निर्धारित करने के लिए कार्य करता है । इष्टतम पथ 1 से शुरू होना चाहिए, प्रत्येक चोटियों को छूना चाहिए, और 1 पर वापस जाना चाहिए। इस मामले में, "सबसे छोटा मार्ग" आवश्यक रूप से सबसे कम चालों वाला नहीं है। यह कम से कम समग्र समय के साथ एक है, जो कि बढ़त वजन में मापा जाता है।
golfed
o=Sequence;v[a_<->b_,z_]:=(m_~u~q_:={Quotient[m-1,q[[2]]]+1,1+Mod[m-1, q[[2]]]};j=z[[o@@u[a,i=Dimensions@z]]];k=z[[o@@u[b,i]]];Which[j==k,{{a,b}->3,{b,a}->3},j==k-1,{{a,b}->11,{b,a}->2},j==k+1,{{a,b}->2,{b,a}->11},2<4,{{a,b}->∞, {b, a}->∞}]);w@e_:=Module[{d,x,l,y},x=Map[ToExpression,Characters/@Drop[StringSplit@e,2],{2}];d_~l~c_:=d[[2]](c[[1]]-1)+c[[2]];g_~y~p_:=(Min[Plus@@(GraphDistance[g,#,#2]&@@@#)&/@(Partition[#,2,1]&/@({1,o@@#,1}&/@Permutations@p))]);y[WeightedAdjacencyGraph[ReplacePart[ConstantArray[∞,{t=Times@@(d=Dimensions@x),t}],Flatten[#~v~x &/@Union@Flatten[EdgeList[GridGraph@Reverse@d,#<->_]&/@Range@(Times@@d),1],1]]], l[Dimensions@x, #] & /@ Position[x, Max@x]]
लंबा, अधिक पठनीय रूप
(*determines a weight (number of minutes) to go from vertex a to b and from b to a*)
weight[a_ <-> b_, dat_]:=
Module[{cellA,cellB,dim,valA,valB,vertexToCell},
(*Convert graph vertex index to cell location*)
vertexToCell[m_,dimen_]:={Quotient[m-1,dim[[2]]]+1,1+Mod[m-1,dimen[[2]]]};
dim=Dimensions[dat];
cellA = vertexToCell[a,dim];
cellB = vertexToCell[b,dim];
valA=dat[[Sequence@@cellA]];
valB=dat[[Sequence@@cellB]];
Which[
valA==valB,{{a,b}-> 3,{b,a}-> 3},
valA==valB-1,{{a,b}-> 11,{b,a}-> 2},
valA==valB+1,{{a,b}-> 2,{b,a}-> 11},
2<4,{{a,b}->∞,{b,a}->∞}]];
(* weights[] determines the edge weights (times to get from one position to the next), makes a graph and infers the shortest distance
from vertex 1 to each peak and back. It tries out all permutations of peaks and
selects the shortest one. Finally, it returns the length (in minutes) of the shortest trip. *)
weights[str_]:=
Module[{d,dat,neighbors,cellToVertex,peaks,z,gd},
dat=Map[ToExpression,Characters/@Drop[StringSplit[str],2],{2}];
cellToVertex[dim_,cell_]:=dim[[2]] (cell[[1]]-1)+cell[[2]];
peaks[dat_]:= cellToVertex[Dimensions[dat],#]&/@Position[dat,peak =Max[dat]];
(* to which cells should each cell be compared? neighbors[] is a function defined within weights[]. It returns a graph, g, from which graph distances will be derived in the function gd[] *)
neighbors[dim_]:=
Union@Flatten[EdgeList[GridGraph[Reverse@dim],#<->_]&/@Range@(Times@@dim),1];
d=Dimensions[dat];
m=ReplacePart[ConstantArray[∞,{t=Times@@d,t}],
(*substitutions=*)
Flatten[weight[#,dat]&/@neighbors[d],1]];
g=WeightedAdjacencyGraph[m,VertexLabels->"Name",ImageSize->Full,GraphLayout->"SpringEmbedding"];
(* finds shortest path. gd[] is also defined within weights[] *)
gd[g3_,ps_]:=
Module[{lists,pairs},
pairs=Partition[#,2,1]&/@({1,Sequence@@#,1}&/@Permutations@ps);
Min[Plus@@(GraphDistance[g3,#,#2]&@@@#)&/@pairs]];
gd[g,peaks[dat]]]
टेस्ट
weights["4 5
32445
33434
21153
12343"]
96।
weights@"2 7
6787778
5777679"
75।
weights@"3 4
1132
2221
1230"
51।
व्याख्या
निम्नलिखित इनपुट के 2-5 लाइनों के बारे में सोचें
"4 5
32445
33434
21153
12343"
4 पंक्तियों और 5 स्तंभों के साथ एक सरणी का प्रतिनिधित्व करने के रूप में:
जहां प्रत्येक शीर्ष इनपुट इनपुट से एक अंक के साथ मेल खाता है: 3 शीर्ष 1 पर है, 2 शीर्ष 2 पर है, 4 शीर्ष 3 पर है, शीर्ष 4 पर एक और 4, शीर्ष 5 पर 5, आदि। ग्रिड ग्राफ केवल एक मोटा है हम जिस ग्राफ का लक्ष्य बना रहे हैं। यह अप्रत्यक्ष है। इसके अलावा, कुछ किनारे अनुपलब्ध होंगे। (याद रखें: हम उस स्थिति से दूसरे स्थान पर नहीं जा सकते हैं, जो वर्तमान में 1 या उससे अधिक ऊँचाई वाली इकाई है।) लेकिन ग्रिड का ग्राफ़ हमें आसानी से उन शीर्ष रेखाओं को खोजने देता है जो किसी भी चयनित शीर्ष के बगल में हैं। यह उन किनारों की संख्या को कम करता है जिन पर हमें विचार करने की आवश्यकता है, पहले उदाहरण में (4 बाय 5 ग्रिड), 400 (20 * 20) से 62 (31 * 2 ग्रिड ग्राफ में किनारों की संख्या)। एक ही उदाहरण में, केवल किनारों में से 48 ऑपरेटिव हैं; 14 नहीं हैं।
निम्नलिखित 20 से 20 भारित आसन्न मैट्रिक्स ग्रिड ग्राफ से कोने के सभी जोड़े के बीच की दूरी का प्रतिनिधित्व करता है।
कुंजी कोड जो यह तय करता है कि किस नंबर को असाइन करना है।
Which[
valA==valB,{{a,b}-> 3,{b,a}-> 3},
valA==valB-1,{{a,b}-> 11,{b,a}-> 2},
valA==valB+1,{{a,b}-> 2,{b,a}-> 11},
2<4,{{a,b}->∞,{b,a}->∞}]
सेल {1,2} - एक-अनुक्रमण में - मान 2 होता है क्योंकि शीर्ष 1 से शीर्ष 2 तक की चाल डाउनहिल है। सेल {2,1} में 11 होते हैं क्योंकि वर्टेक्स 2 से वर्टेक्स 1 तक की चाल चढती है। कोशिकाओं के 3 {1,6} और {6,1} संकेत देते हैं कि आंदोलन न तो ऊपर है और न ही नीचे है। सेल {1,1} में ∞ शामिल है क्योंकि यह स्वयं से जुड़ा नहीं है।
निम्नलिखित ग्राफ उपरोक्त इनपुट को अंतर्निहित संरचना को दर्शाता है। रंगीन तीर शीर्ष 1 से चोटियों (5 और 14 पर) तक का इष्टतम मार्ग दिखाते हैं और वापस 1. 1. नीले तीर एक ही स्तर (3 मिनट) पर चलने के लिए मेल खाते हैं; लाल तीर का अर्थ है चढ़ाई (11 मिनट) और हरा तीर वंश (2 मिनट) को दर्शाता है।
शीर्ष 1 से पथ (सेल {1,1} से दो शिखरों तक और पीछे 1)
3 + 3 + 11 + 3 + 3 + 11 + 2 + 2 + 3 + 11 + 11 + 2 + 2 + 2 + 2 + 11 + 11 + 3
96