Skip to content

Commit

Permalink
Added elevation gain optimization
Browse files Browse the repository at this point in the history
  • Loading branch information
zbycz committed Jul 1, 2013
2 parents 7e5ccee + f899f0b commit 30e8eb0
Show file tree
Hide file tree
Showing 18 changed files with 429 additions and 30 deletions.
8 changes: 5 additions & 3 deletions src/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ LD=gcc

# Compilation program options

CFLAGS=-Wall -Wmissing-prototypes -std=c99
CFLAGS=-Wall -Wmissing-prototypes #-std=c99
#CFLAGS+=-Wextra -pedantic
LDFLAGS=-lm

Expand Down Expand Up @@ -87,7 +87,8 @@ PLANETSPLITTER_OBJ=planetsplitter.o \
files.o logging.o \
results.o queue.o sorting.o \
xmlparse.o tagging.o \
uncompress.o osmxmlparse.o osmpbfparse.o osmo5mparse.o osmparser.o
uncompress.o osmxmlparse.o osmpbfparse.o osmo5mparse.o osmparser.o \
srtmHgtReader.o

planetsplitter : $(PLANETSPLITTER_OBJ)
$(LD) $(PLANETSPLITTER_OBJ) -o $@ $(LDFLAGS)
Expand All @@ -100,7 +101,8 @@ PLANETSPLITTER_SLIM_OBJ=planetsplitter-slim.o \
files.o logging.o \
results.o queue.o sorting.o \
xmlparse.o tagging.o \
uncompress.o osmxmlparse.o osmpbfparse.o osmo5mparse.o osmparser.o
uncompress.o osmxmlparse.o osmpbfparse.o osmo5mparse.o osmparser.o \
srtmHgtReader.o

planetsplitter-slim : $(PLANETSPLITTER_SLIM_OBJ)
$(LD) $(PLANETSPLITTER_SLIM_OBJ) -o $@ $(LDFLAGS)
Expand Down
4 changes: 2 additions & 2 deletions src/osmparser.c
Original file line number Diff line number Diff line change
Expand Up @@ -638,7 +638,7 @@ void ProcessWayTags(TagList *tags,int64_t way_id,int mode)

way.type=Highway_None;

AppendSegmentList(segments,id,NO_NODE_ID,NO_NODE_ID,0);
AppendSegmentList(segments,id,NO_NODE_ID,NO_NODE_ID,0,0,0,0,0);
}

if(mode==MODE_DELETE)
Expand Down Expand Up @@ -1046,7 +1046,7 @@ void ProcessWayTags(TagList *tags,int64_t way_id,int mode)
logerror("Node %"Pnode_t" in way %"Pway_t" appears more than once.\n",to,id);

if(!duplicated)
AppendSegmentList(segments,id,from,to,area+oneway);
AppendSegmentList(segments,id,from,to,area+oneway, 0,0,0,0); //TODO: may have non-zero ascent/descent?
}
}
}
Expand Down
25 changes: 25 additions & 0 deletions src/planetsplitter.c
Original file line number Diff line number Diff line change
Expand Up @@ -504,6 +504,31 @@ if(!option_process_only)

SortTurnRelationListGeographically(Relations,Nodes,Segments);


// //check if there are bad data somewhere
// SegmentsX * segmentsx = Segments;
// SegmentX segmentx;
// int index=0;
// /* Open the file read-only */
// segmentsx->fd=ReOpenFile(segmentsx->filename_tmp);
// /* Read the on-disk image */
// while(!ReadFile(segmentsx->fd,&segmentx,sizeof(SegmentX)))
// {
// if(isnan(segmentx.ascent))
// fprintf(stderr, "read: id%d sup%d, node(%u,%u) ad(%.1f,%.1f)\n", index, (segmentx.distance&SEGMENT_SUPER != 0), segmentx.node1, segmentx.node2, segmentx.ascent, segmentx.descent);
//
// index++;
// }
// /* Close the file */
// segmentsx->fd=CloseFile(segmentsx->fd);
// /* Print the final message */







/* Output the results */

printf("\nWrite Out Database Files\n========================\n\n");
Expand Down
2 changes: 2 additions & 0 deletions src/profiles.h
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,8 @@ typedef struct _Profile
height_t height; /*+ The minimum height of vehicles on the route. +*/
width_t width; /*+ The minimum width of vehicles on the route. +*/
length_t length; /*+ The minimum length of vehicles on the route. +*/

float hills;
}
Profile;

Expand Down
6 changes: 6 additions & 0 deletions src/results.c
Original file line number Diff line number Diff line change
Expand Up @@ -208,6 +208,12 @@ Result *InsertResult(Results *results,index_t node,index_t segment)
result->score=0;
result->sortby=0;

//not sure if its here correctly
result->ascent=0;
result->descent=0;
result->ascentOn=0;
result->descentOn=0;

result->queued=NOT_QUEUED;

return(result);
Expand Down
5 changes: 5 additions & 0 deletions src/results.h
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,11 @@ struct _Result
score_t score; /*+ The best actual weighted distance or duration score from the start to the node. +*/
score_t sortby; /*+ The best possible weighted distance or duration score from the start to the finish. +*/

float ascent;
float descent;
float ascentOn;
float descentOn;

uint32_t queued; /*+ The position of this result in the queue. +*/
};

Expand Down
11 changes: 8 additions & 3 deletions src/router.c
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,7 @@ int main(int argc,char** argv)
index_t start_node=NO_NODE,finish_node=NO_NODE;
index_t join_segment=NO_SEGMENT;
int arg,point;
float hills = 0;

/* Parse the command line arguments */

Expand Down Expand Up @@ -346,11 +347,15 @@ int main(int argc,char** argv)
profile->height=metres_to_height(atof(&argv[arg][9]));
else if(!strncmp(argv[arg],"--width=",8))
profile->width=metres_to_width(atof(&argv[arg][8]));
else if(!strncmp(argv[arg],"--length=",9))
profile->length=metres_to_length(atof(&argv[arg][9]));
else if(!strncmp(argv[arg],"--length=",9)) //hills supplied via length parameter
hills=atof(&argv[arg][9]);
//profile->length=metres_to_length(atof(&argv[arg][9]));
else if(!strncmp(argv[arg],"--hills=",8))
hills=atof(&argv[arg][8]);
else
print_usage(0,argv[arg],NULL);
}
profile->hills = hills; //zero means no optimization

for(point=1;point<=NWAYPOINTS;point++)
if(point_used[point]==1 || point_used[point]==2)
Expand Down Expand Up @@ -433,7 +438,7 @@ int main(int argc,char** argv)
fprintf(stderr,"Error: Profile is invalid or not compatible with database.\n");
return(1);
}

/* Loop through all pairs of points */

for(point=1;point<=NWAYPOINTS;point++)
Expand Down
44 changes: 39 additions & 5 deletions src/segments.c
Original file line number Diff line number Diff line change
Expand Up @@ -219,24 +219,58 @@ duration_t Duration(Segment *segmentp,Way *wayp,Profile *profile)
{
speed_t speed1=wayp->speed;
speed_t speed2=profile->speed[HIGHWAY(wayp->type)];
int final;
distance_t distance=DISTANCE(segmentp->distance);

if(speed1==0)
{
if(speed2==0)
return(hours_to_duration(10));
else
return distance_speed_to_duration(distance,speed2);
final = speed2;
}
else /* if(speed1!=0) */
{
if(speed2==0)
return distance_speed_to_duration(distance,speed1);
final = speed1;
else if(speed1<=speed2)
return distance_speed_to_duration(distance,speed1);
final = speed1;
else
return distance_speed_to_duration(distance,speed2);
final = speed2;
}

float hills = profile->hills;
if(hills == 0 || segmentp->ascentOn == 0)
return distance_speed_to_duration(distance, final);

//hill's percentage
float percent = segmentp->ascent/segmentp->ascentOn*100;
printf("hill: %0.2f speed %d ", percent, final);

//special output for precomputed speeds
if(hills >= 100){
if(percent > 2) final = 15;
if(percent > 4) final = 10;
if(percent > 7) final = 8;
if(percent > 9) final = 6;
if(percent > 15) final = 3;
}
else { //linear slowing ($hills = speed on 10% hill)
speed_t maxi = final;
final = -((maxi-hills)/10) * percent + maxi;

if(final < 3) final = 3;
}


//printf("distance %d, proc %0.2f, ascent %0.1f on %0.1f ", distance, percent, segmentp->ascent, segmentp->ascentOn);
//distance = percent * distance;

printf("final %d\n", final);



return distance_speed_to_duration(distance, final);
}


Expand Down
5 changes: 5 additions & 0 deletions src/segments.h
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,11 @@ struct _Segment
index_t way; /*+ The index of the way associated with the segment. +*/

distance_t distance; /*+ The distance between the nodes. +*/

float ascent;
float descent;
float ascentOn;
float descentOn;
};


Expand Down
51 changes: 47 additions & 4 deletions src/segmentsx.c
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,8 @@
#include "logging.h"
#include "sorting.h"

#include "srtmHgtReader.h"


/* Global variables */

Expand Down Expand Up @@ -159,7 +161,7 @@ void FreeSegmentList(SegmentsX *segmentsx,int keep)
distance_t distance The distance between the nodes (or just the flags).
++++++++++++++++++++++++++++++++++++++*/

void AppendSegmentList(SegmentsX *segmentsx,way_t way,node_t node1,node_t node2,distance_t distance)
void AppendSegmentList(SegmentsX *segmentsx,way_t way,node_t node1,node_t node2,distance_t distance, float ascent, float descent, float ascentOn, float descentOn)
{
SegmentX segmentx;

Expand All @@ -173,13 +175,26 @@ void AppendSegmentList(SegmentsX *segmentsx,way_t way,node_t node1,node_t node2,

if(distance&(ONEWAY_2TO1|ONEWAY_1TO2))
distance^=ONEWAY_2TO1|ONEWAY_1TO2;

float tmp;
tmp=ascent;
ascent=descent;
descent = tmp;

tmp=ascentOn;
ascentOn=descentOn;
descentOn=ascentOn;
}

segmentx.node1=node1;
segmentx.node2=node2;
segmentx.next2=NO_SEGMENT;
segmentx.way=way;
segmentx.distance=distance;
segmentx.ascent=ascent;
segmentx.descent=descent;
segmentx.ascentOn=ascentOn;
segmentx.descentOn=descentOn;

WriteFile(segmentsx->fd,&segmentx,sizeof(SegmentX));

Expand Down Expand Up @@ -695,20 +710,44 @@ void MeasureSegments(SegmentsX *segmentsx,NodesX *nodesx,WaysX *waysx)

NodeX *nodex1=LookupNodeX(nodesx,node1,1);
NodeX *nodex2=LookupNodeX(nodesx,node2,2);

TSrtmAscentDescent ad;

/* Replace the node and way ids with their indexes */

segmentx.node1=node1;
segmentx.node2=node2;
segmentx.way =way;

SetBit(segmentsx->usedway,segmentx.way);

/* Set the distance but keep the other flags except for area */

segmentx.distance=DISTANCE(DistanceX(nodex1,nodex2))|DISTFLAG(segmentx.distance);
segmentx.distance&=~SEGMENT_AREA;


/* Compute the ascent descent */

ad = srtmGetAscentDescent(
radians_to_degrees(latlong_to_radians(nodex1->latitude)), radians_to_degrees(latlong_to_radians(nodex1->longitude)),
radians_to_degrees(latlong_to_radians(nodex2->latitude)), radians_to_degrees(latlong_to_radians(nodex2->longitude)),
(int)DISTANCE(segmentx.distance));

segmentx.ascent = ad.ascent;
segmentx.descent = ad.descent;
segmentx.ascentOn = ad.ascentOn;
segmentx.descentOn = ad.descentOn;

//fprintf(stderr, "measure%d: ", index);
////fprintf(stderr, "node(%u,%u) ", node1, node2);
////fprintf(stderr, "node(%0.5f,%0.5f) (%0.5f,%0.5f) ", radians_to_degrees(latlong_to_radians(nodex1->latitude)), radians_to_degrees(latlong_to_radians(nodex1->longitude)), radians_to_degrees(latlong_to_radians(nodex2->latitude)), radians_to_degrees(latlong_to_radians(nodex2->longitude)));

//fprintf(stderr, "dist(%d) ", DISTANCE(segmentx.distance));
//fprintf(stderr, "ad(%.1f,%.1f)\n", ad.ascent, ad.descent);
//fprintf(stderr, "adon(%.1f,%.1f)\n", ad.ascentOn, ad.descentOn);



/* Write the modified segment */

WriteFile(fd,&segmentx,sizeof(SegmentX));
Expand Down Expand Up @@ -747,7 +786,7 @@ void MeasureSegments(SegmentsX *segmentsx,NodesX *nodesx,WaysX *waysx)


/*++++++++++++++++++++++++++++++++++++++
Index the segments by creating the firstnode index and filling in the segment next2 parameter.
Index the segments by creating the firstnode index and filling in the segment next2 parameter (like linked list)
SegmentsX *segmentsx The set of segments to modify.
Expand Down Expand Up @@ -1167,6 +1206,10 @@ void SaveSegmentList(SegmentsX *segmentsx,const char *filename)
segment.next2 =segmentx.next2;
segment.way =segmentx.way;
segment.distance=segmentx.distance;
segment.ascent =segmentx.ascent;
segment.descent =segmentx.descent;
segment.ascentOn=segmentx.ascentOn;
segment.descentOn=segmentx.descentOn;

if(IsSuperSegment(&segment))
super_number++;
Expand Down
7 changes: 6 additions & 1 deletion src/segmentsx.h
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,11 @@ struct _SegmentX
way_t way; /*+ The id of the way; initially the OSM value, later the WayX index. +*/

distance_t distance; /*+ The distance between the nodes. +*/

float ascent;
float descent;
float ascentOn;
float descentOn;
};


Expand Down Expand Up @@ -85,7 +90,7 @@ struct _SegmentsX
SegmentsX *NewSegmentList(int append,int readonly);
void FreeSegmentList(SegmentsX *segmentsx,int keep);

void AppendSegmentList(SegmentsX *segmentsx,way_t way,node_t node1,node_t node2,distance_t distance);
void AppendSegmentList(SegmentsX *segmentsx,way_t way,node_t node1,node_t node2,distance_t distance, float ascent, float descent, float ascentOn, float descentOn);
void FinishSegmentList(SegmentsX *segmentsx);

SegmentX *FirstSegmentX(SegmentsX *segmentsx,index_t nodeindex,int position);
Expand Down
Loading

0 comments on commit 30e8eb0

Please sign in to comment.