Check alle échte Black Friday-deals Ook zo moe van nepaanbiedingen? Wij laten alleen échte deals zien
Toon posts:

[js] architectuur

Pagina: 1
Acties:

Verwijderd

Topicstarter
Ik heb een probleem met het opzetten van m'n js architectuur, de algorithhhhmes is het probleem niet, maar ik kom er even niet uit hoe ik een en ander netjes in elkaar draai, dus tips zijn wat dat betreft welkom.

Ik heb een prototype, TimeWindow wat een periode in de tijd voorsteld. Dit prototype heeft onder andere een from en een to property. Hiervan afgeleid is een ander prototype, TaskWindow, wat ook nog een name en een numberOfPeopleNeeded property heeft. Dit stelt een taak voor, die een bepaalde periode in de tijd beslaat en een naam en aantal personen die die taak uit moeten gaan voeren heeft:

JavaScript:
1
2
3
function TimeWindow(from,to) {}
function TaskWindow(from,to,name,numberOfPeopleNeeded) {}
TaskWindow.prototype = new TimeWindow();


Nu heb ik een setje operaties die plaatsvinden op arrays van TimeWindows, namelijk het uitrekenen van de unie, intersectie en verschil van twee arrays van TimeWindows. Aangezien dit operaties zijn op arrays, is dit dus niet te implementeren als method van de prototypes. Wat ik nu even heb gedaan is ze implementeren als static van het TimeWindow prototype:

JavaScript:
1
2
3
TimeWindow.unite = function(twArray1,twArray2){}
TimeWindow.intersect = function(twArray1,twArray2){}
TimeWindow.subtract = function(twArray1,twArray2){}


Deze functies maken op hun beurt allemaal weer gebruik van eenzelfde functionaliteit, die ik dus voor het gemak maar even naar buiten heb gehaald. Dit is namelijk het berekenen van de zgn edgeMap van een array van windows. Deze geeft een op tijd gesorteerde array terug van alle begin en eind tijdstippen van de windows in het array.

Wat nu het geval is, is dat voor taskWindows precies hetzelfde moet gebeuren, alleen dan zijn die functies een klein beetje anders, wat zich dus perfect leent voor wat overerving, maar dat is in deze setup dus een tikje niet te doen

Dus:
- ik ben niet helemaal gelukkig met de huidige setup
- ik wil ongeveer dezelfde functies implementeren voor arrays van TaskWindows
- hoe kan ik dit nou het netste doen?

  • crisp
  • Registratie: Februari 2000
  • Nu online

crisp

Devver

Pixelated

Persoonlijk zou ik dit doen:
JavaScript:
1
2
function TaskWindow(from,to,name,numberOfPeopleNeeded) {}
Object.extend(TaskWindow.prototype, TimeWindow.prototype);

(Object.extend geleend vanuit prototype)

Intentionally left blank


Verwijderd

Topicstarter
Dat is hip voor de manier waarop ik m'n prototype extend, maar hoe helpt me dat met het netjes neerzetten van die functies op 2 arrays?

  • crisp
  • Registratie: Februari 2000
  • Nu online

crisp

Devver

Pixelated

Verwijderd schreef op maandag 06 augustus 2007 @ 11:17:
Dat is hip voor de manier waarop ik m'n prototype extend, maar hoe helpt me dat met het netjes neerzetten van die functies op 2 arrays?
Op dezelfde manier zou je dit kunnen doen voor de 'static' methods:
JavaScript:
1
Object.extend(TaskWindow, TimeWindow);

otoh zou je binnen TaskWindow natuurlijk ook gewoon de static methods van TimeWindow kunnen aanroepen, ware het niet dat dit mij wel enigszins zorgen baart:
alleen dan zijn die functies een klein beetje anders
hoe zijn die functies een 'beetje anders'? Leent het zich dan ueberhaupt wel voor 'overerving' (meer overkopieering in mijn voorbeeld ;))?

Overigens kan je natuurlijk binnen die functies instanceof gebruiken om te kijken of een object een instance is van TaskWindow of van TimeWindow - wellicht kan je daar de verschillen mee afvangen.

[ Voor 11% gewijzigd door crisp op 06-08-2007 11:26 ]

Intentionally left blank


Verwijderd

Topicstarter
Ik neig eigenlijk naar het gebruiken van een TimeWindowCollection prototype als vervanging van die array, en dan daaraan die edgeMap, unite, intersect en subtract hangen. Dan kan ik ook een TaskWindowCollection maken die daarvan afgeleid is.

Het verschil zit het in de edgeMap method, die voor TaskWindows anders is (hij behandelt een taskWindow als meerdere timeWindows voor verschillende personen)

checken met instanceof zat ik ook aan te denken, maar het is een beetje maf (imho) om in een superobject te kijken of de parameter een instantie is van een subobject

  • crisp
  • Registratie: Februari 2000
  • Nu online

crisp

Devver

Pixelated

Jep, een apart object-type voor de collectie makes sense, en dan zoiets:
JavaScript:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
function TimeWindow()
{
  this.collection = new TimeWindowCollection();
}
TimeWindow.prototype.add = function(from, to)
{
  this.collection.push(
    {
      from: from,
      to: to
    }
  );
}
// etcetera, overerving enzo

var globalTimeWindow = new TimeWindow();
var globalTaskWindow = new TaskWindow();

globalTimeWindow.add(from, to);
globalTimeWindow.collection.unite();

Intentionally left blank


Verwijderd

Verwijderd schreef op maandag 06 augustus 2007 @ 09:03:
alleen dan zijn die functies een klein beetje anders, wat zich dus perfect leent voor wat overerving
Misschien begrijp ik je verkeerd maar als de functies anders zijn (ook al is het een klein beetje) dan leent het zich toch juist niet echt voor overerving?

Hoewel het op zich logisch klinkt om een collection object te implementeren die union/intersect/etc methodes heeft zou ik zelf toch voor 'helper' functies gaan of de static methods uit je eerste post. 't Is vooral een gevoelskwestie maar ik zie geen goede reden om dit soort operaties aan de objecten zelf te hangen. Zeker niet als de argumenten zelf niet gemodificeerd worden door de operaties. (ik neem aan dat c = intersect(a, b); geen effect heeft op a en b)

Verwijderd

Topicstarter
ik heb het ondertussen met een collection object gedaan, alleen nu staan collection en part een beetje "los" van elkaar. Crisps idee om dat wat meer in elkaar te kleien vind ik op zich ook wel aardig.

Het grote verschil tussen m'n timeWindows en taskWindows is dat de laatste een "weight" hebben en dus in principe een x-aantal losse timeWindows voorstellen (met een naam ook nog eens)

unite en intersect (en ook subtract wat intersecten met een negated is) zijn dus in feite boolean operaties, terwijl een subtract op een taskWindow meer een integer operatie is, ter illustratie:
code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
unite timewindows
[=========]        [========]     [=========]
    [========]        [====]                   [====]
_____________________________________________________
[============]     [========]     [=========]  [====]

intersect timewindows
[=========]        [========]     [=========]
    [========]        [====]                   [====]
_____________________________________________________
    [=====]           [====]  
   
subtract timewindows    
[=========]        [========]     [=========]
    [========]        [====]                   [====]
_____________________________________________________
[===]              [==]    []     [=========]

add taskwindows    
[222222222]        [11111111]     [333333333]
    [11111111]        [1111]                   [2222]
_____________________________________________________
[222|33333|11]     [11|2222|]     [333333333]  [2222]

subtract taskwindows    
[222222222]        [11111111]     [333333333]
    [11111111]        [1111]                   [2222]
_____________________________________________________
[222|11111]        [11]    []     [333333333]

waar bij de laatste operatie negatieve of 0-windows niet tellen

de operaties voer ik uit door van een collection eerst een edgeMap te maken, da's een array van alle begin- of eind tijdstippen van de intervallen, waaraan een nummertje wordt gehangen: 1 als een window begint, -1 als ie eindigt, voor taskWindows wordt dat vermenigvuldigd met de weight

dit impliceert dus al een aparte edgemap method voor beide typen collection

nu is de intersectie en unie makkelijk uit te rekenen door te kijken of de lopende som van de edgemap boven de 2, resp de 1 zit. Verschil is voor de TimeWindow een intersectie met de negatie (1 en -1 in de edgemap uitwisselen)

voor de taskWindows is het verschil een andere operatie, namelijk een integer operatie in essentie, deze moet dus hergedefinieerd worden. Verder zou een optel method ook nuttig zijn, al heb ik deze niet direct nodig. Intersectie en Unie zijn hetzelfde, dus die kan ik overerven (cq kopieren)

Hoop dat dat een beetje het idee verduidelijkt. Het werkt nu allemaal (weer) met een compleet losse collection object waarvoor de bovenstaande methods geimplementeerd zijn. Het voelt wel een beetje raar dat die dingen toch wat los van elkaar staan, terwijl ze toch heel erg erg met elkaar te maken hebben, vandaar dat ik crisps aanpak ook wel aardig vind

Verder nog een klein probleempje met aaneensluitende intervallen, je krijgt dan extra windows met lengte 0, maar da's niets wat niet op te lossen valt :)

concreet antwoord op blues: met functie bedoel ik hier niet "method" maar meer "functionaliteit", die bestaat uit het uitvoeren van een method die weer andere aanroept (die edgemap method bijvoorbeeld). Het kleine verschil in functionaliteit zit hem in een paar methods, de rest is allemaal hetzelfde.

[ Voor 4% gewijzigd door Verwijderd op 07-08-2007 09:24 ]

Pagina: 1