2017-04-01 46 views
10

मैं एक सीमित तत्व पुस्तकालय को डिजाइन करने की प्रक्रिया में हूं। किसी दिए गए समस्या के लिए, परिमित तत्व जाल में विभिन्न आयामों के तत्व हो सकते हैं (उदाहरण के लिए टेट्राहेड्रा और त्रिकोण), और समान आयाम के विभिन्न तत्वों को संयोजित करना भी संभव है (उदाहरण के लिए टेट्राहेड्रा और हेक्साहेड्रा)। इसलिए, मुझे एक डेटा संरचना की आवश्यकता है जो सीमित तत्वों की जानकारी संग्रहीत करे। सबसे मौलिक जानकारी तत्वों की कनेक्टिविटी (नोड आईडी जो तत्व को परिभाषित करती है) है। उदाहरण के लिए, मुझे किसी भी तरह से स्टोर करने की आवश्यकता है कि त्रिभुज तत्व 4 नोड्स 5, 6, और 10.जटिल डेटा संरचना की निर्भरताओं को डिजाइन करना

मेरा पहला प्रयास एक सूची बनाना था जिसका सूचकांक आयाम (0,1,2 या 3) है और जो शब्दकोश भंडार करता है। इन शब्दकोशों में स्ट्रिंग कुंजियां (पहचानकर्ता) होती हैं और मान numpy arrays (प्रत्येक पंक्ति तत्व कनेक्टिविटी का प्रतिनिधित्व करते हैं) हैं। मुझे ऐसा करने की ज़रूरत है क्योंकि दिए गए आयाम के लिए numpy arrays स्ट्रिंग पहचानकर्ताओं के आधार पर अलग-अलग आकार होते हैं।

इस वर्ग है:

import os 
from collections import OrderedDict 
import numpy.ma as ma 

flatten = lambda l: [item for sublist in l for item in sublist] 

class ElementData(list): 

    def __init__(self, *args, **kwargs): 

     self.reset() 
     super(ElementData, self).__init__(*args, **kwargs) 

    def __iter__(self): 
     for k, v in self[self.idx].items(): 
      for i, e in enumerate(v): 
       yield (k,i,e) if not ma.is_masked(e) else (k,i, None) 
     self.reset() 


    def __call__(self, idx): 
     self.idx = idx-1 
     return self 

    def __getitem__(self, index): 
     if index >= len(self): 
      self.expand(index) 
     return super(ElementData, self).__getitem__(index) 

    def __setitem__(self, index, value): 
     if index >= len(self): 
      self.expand(index) 
     list.__setitem__(self, index, value) 

    def __str__(self): 
     return "Element dimensions present: {}\n".format([i for i in range(len(self)) if self[i]]) + super(ElementData, self).__str__() 

    def keys(self): 
     return flatten([list(self[i].keys()) for i in range(len(self))]) 

    def reset(self): 
     self.idx = -1 
     self.d = -1 

    def expand(self, index): 
     self.d = max(index, self.d) 
     for i in range(index + 1 - len(self)): 
      self.append(OrderedDict()) 

    def strip(self, value=None): 
     if not callable(value): 
      saved_value, value = value, lambda k,v: saved_value 
     return ElementData([OrderedDict({k:value(k, v) for k,v in i.items()}) for i in super(ElementData, self).__iter__()]) 


    def numElements(self, d): 

     def elementsOfDimension(d): 
      # loop over etypes 
      nelems = 0 
      for v in self[d].values(): 
       nelems += v.shape[0] if not isinstance(v, ma.MaskedArray) else v.shape[0] - v.mask.any(axis=1).sum() 
      return nelems 

     # compute the number of all elements 
     if d == -1: 
      nelems = 0 
      for i in range(self.d+1): 
       nelems += elementsOfDimension(i) 
      return nelems 
     else: # of specific dimension only 
      return elementsOfDimension(d) 

वर्ग अच्छी तरह से काम करता है, और यह मूल किसी विशेष आयाम के सभी आइटम्स लूप करने के लिए मुझे अनुमति देता है। हालांकि, प्रत्येक तत्व से जुड़े अन्य डेटा हैं जो अलग से संग्रहीत हैं, उदाहरण के लिए इसकी सामग्री। इसलिए, मैंने अन्य गुणों के संदर्भ में एक ही डेटा संरचना का उपयोग करने का निर्णय लिया। उस अंत में मैं कक्षा के strip फ़ंक्शन का उपयोग करता हूं, ताकि मुझे पूरी संरचना को बिना किसी सरणी के लौटा सकें।

समस्या यह है कि मैं मूल डेटा संरचना गतिशील है, और यदि मैं इसे बदलता हूं, तो मुझे उस पर निर्भर अन्य सभी संरचनाओं को संशोधित करना होगा। मुझे सच में लगता है कि इस वर्ग को डिजाइन करते समय मैं गलत दिशा में गया था। शायद इस समस्या से निपटने का एक आसान तरीका है? मैंने numpy arrays (उदाहरण के लिए tuples के रूप में) के बगल में अतिरिक्त जानकारी संग्रहीत करने के बारे में सोचा, लेकिन मुझे नहीं पता कि यह अच्छा है या नहीं। सॉफ़्टवेयर डिज़ाइन करते समय किए गए विकल्प वास्तव में बाद में हमारे जीवन को दुखी कर सकते हैं, और अब मुझे यह एहसास हो रहा है।

अद्यतन

श्रेणी से ऊपर का उपयोग करना, एक उदाहरण निम्नलिखित हो सकता है:

Element dimensions present: [0, 1, 2] 
[OrderedDict([('n1', array([[0], 
     [1], 
     [3]]))]), OrderedDict([('l2', array([[1, 2]]))]), OrderedDict([('q4', array([[0, 1, 5, 4], 
     [5, 1, 2, 6], 
     [6, 2, 3, 7], 
     [7, 3, 0, 4], 
     [4, 5, 6, 7]]))])] 

जहां डेटा संरचना 0 (नोड) के तत्वों, 1 (लाइन) स्टोर करने के लिए इस्तेमाल किया गया है और 2 (चतुर्भुज) आयाम।

+0

शायद यह समझने में सहायता करेगा कि आपने इस डेटा संरचना को शुरुआत में क्यों बनाया है। आप क्या समस्या हल कर रहे हैं? – plalx

+0

मैं एक परिमित तत्व पुस्तकालय बना रहा हूँ। उन numpy arrays में प्रत्येक पंक्ति एक तत्व कनेक्टिविटी (नोड आईडी जो तत्व को परिभाषित करती है) है। किसी दिए गए समस्या के लिए, परिमित तत्व जाल में विभिन्न आयामों (उदाहरण के लिए टेट्राहेड्रा और त्रिकोण) के तत्व हो सकते हैं, और समान आयाम के विभिन्न तत्वों को संयोजित करना भी संभव है (उदाहरण के लिए टेट्राहेड्रा और हेक्साहेड्रा फिट बैठता है। लेकिन यह पहला डेटा संरचना केवल सौदों के साथ है तत्वों की कनेक्टिविटीज। प्रत्येक तत्व को एक भौतिक संपत्ति भी सौंपी जाती है (जिसके लिए मुझे सामग्री भंडारण के लिए एक और डेटा संरचना की आवश्यकता होती है), और अन्य डेटा के लिए भी। – aaragon

+0

कृपया अपने प्रश्न में कुछ डेटा प्रदान करें जो ** परिवर्तन ** दिखाएं, एक जो दिए गए 'वर्ग' के साथ काम करता है और एक बदलता है जो फिट नहीं होता है। मेरा पहला प्रयास गायब 'एम। मास्कडएरे' के साथ असफल रहा, जहां यह आ गया। – stovfl

उत्तर

0

जब "जटिल डेटा संरचना की निर्भरता" कहा जाता है, तो आप शायद "ग्राफ" के बारे में बात कर सकते हैं, क्या आपने दोहरी जांच की है कि क्या कोई मौजूदा graph theory आपकी आवश्यकताओं के अनुरूप है?

+0

मैं ग्राफ से परिचित होने से अधिक हूं, और ये निश्चित रूप से मुझे आवश्यक डेटा संरचना नहीं हैं। – aaragon

2

टिप्पणी ("रूट समस्याओं" की तरह): डिजाइन कार्यक्रम के तार्किक संरचना के खिलाफ जाता है।

मैंने दिए गए एलिमेंट डेटा उदाहरण का उपयोग किया और पूरी तस्वीर को एक बार में प्राप्त करने की उम्मीद नहीं की थी।

टिप्पणी: प्रत्येक तत्व की अनन्य आयाम (एक त्रिकोण हमेशा 2, आयाम है के रूप में एक चतुर्पाश्वीय हमेशा 3 और एक नोड आयाम 0 आयाम है) है।

क्षमा करें, मैंने प्रश्न से गलत व्याख्या की "... विभिन्न आयामों के तत्व ...। तत्व " के साथ" विभिन्न आयामों "मैं अपने प्रस्ताव अनुकूलित है

टिप्पणी:। ... समस्या पैदा होती है जब मैं डेटा संरचना संशोधित (उदाहरण के लिए जोड़ने तत्वों द्वारा)

जब तक आप इस समस्या, मैं एक समाधान ऊपर सोच नहीं कर सकते हैं के लिए एक डाटा उदाहरण प्रदर्शित नहीं करते।


मेरे प्रस्ताव:

class Dimension(object): 
    """ 
    Base class for all Dimensions 
    Dimension has no knowledge to what the data belongs to 
    """ 
    def __init__(self, data=None): 
     pass 

class Element(object): 
    """ 
    Base class for all Elements 
    Hold on class Dimension(object): 
    """ 
    def __init__(self, dimension=None): 
     pass 

class Triangle(Element): 
    def __init__(self, dimension): 
     super().__init__(dimension=dimension) 

class Tetrahedron(Element): 
    def __init__(self, dimension): 
     super().__init__(dimension=dimension) 

class Node(Element): 
    def __init__(self, dimension): 
     super().__init__(dimension=dimension) 

प्रयोग: अपने उदाहरण का निर्माण तत्व

node = Node(dimension=[0,1,3]) 
line = Triangle(dimension=[0,2]) 
quad = Tetrahedron(dimension=[[0, 1, 5, 4], [5, 1, 2, 6], [6, 2, 3, 7], [7, 3, 0, 4], [4, 5, 6, 7]]) 

नए भविष्य तत्व, केवल class Element दिखाने के लिए बढ़ा सकता है:

# New future dimensions - No changes to class Element() required 
class FutureNodTriTet(Element): 
    def __init__(self, dimension): 
     super().__init__(dimension=dimension) 

future_NTT = FutureNodTriTet(dimension=[0, (1,3), (4,5,6)]) 

कृपया टिप्पणी करता है, तो यह है आपकी जरूरतों के करीब।

+0

आपके उत्तर के लिए धन्यवाद। हालांकि दिलचस्प है, डिजाइन कार्यक्रम की तार्किक संरचना के खिलाफ चला जाता है। प्रत्येक तत्व में एक अद्वितीय आयाम होता है (एक त्रिभुज हमेशा आयाम 2 होता है, क्योंकि टेट्राहेड्रॉन हमेशा आयाम 3 और नोड आयाम 0 होता है)। जिस संरचना को मैंने डिजाइन किया है वह काफी अच्छी तरह से काम करता है। हालांकि, जैसा कि मैंने सवाल में कहा था, समस्या तब उत्पन्न होती है जब मैं डेटा संरचना को संशोधित करता हूं (उदाहरण के लिए तत्व जोड़कर), क्योंकि सभी डेटा बिखरे हुए हैं (सामग्री को एक अलग डेटा संरचना में रखा जाता है)। मुझे लगता है कि डेटा को एक साथ रखने के लिए मुझे क्या चाहिए। – aaragon

+0

@ अलागोन: आपकी टिप्पणी के लिए मेरा उत्तर अपडेट किया गया – stovfl

संबंधित मुद्दे