BookmarkSubscribeRSS Feed
norachanisara
Calcite | Level 5

My SAS code  is generating semantic error. It is saying ERROR: The array element 'travel_time[1,2]' has no value at line 228 column 57.

 

I am not sure what that means. I believe the data is completed and has been loaded in correctly. 

 

/* Patient data: duration of treatment and revenue */
data patient_data;
    input i duration revenue;
    datalines;
1   12  200
2   45  181
3   90  255
4   26  150
5   75  220
6   60  200
7   45  180
8   120 300
9   90  250
10  30  158
;
run;

/* Travel times between patients (symmetric for simplicity) */
data travel_times;
    input i j t;
    datalines;
1  2  15
1  3  20
1  4  25
1  5  30
1  6  3.5
1  7  11
1  8  26
1  9  12
1  10  26
2  3  10
2  4  18
2  5  22
2  6  10
2  7  3
2  8  4
2  9  5.5
2  10  15
3  4  12
3  5  15
3  6  10
3  7  25
3  8  30
3  9  22
3  10  12
4  5  8
4  6  23
4  7  10
4  8  7.5
4  9  6.5
4  10  48
5  6  28
5  7  10
5  8  15
5  9  16
5  10  45
6  7  28
6  8  45
6  9  30
6  10  25
7  8  12
7  9  10
7  10  4
8  9  3.5
8  10  15
9  10  30
1  1  0
2  2  0
3  3  0
4  4  0
5  5  0
6  6  0
7  7  0
8  8  0
9  9  0
10  10  0
;
run;

/* Generate full travel time matrix */
data travel_times_full;
    set travel_times;
    output;
    t_temp = t;
    t = t_temp;
    i_temp = i;
    i = j;
    j = i_temp;
    output;
run;

/* Add diagonal elements (travel time to self = 0) */
data travel_times_final;
    set travel_times_full;
    do i = 1 to 10;
        j = i;
        t = 0;
        output;
    end;
run;

/* Nurse and vehicle data */
data nurse_data;
    input H_t H_c c_t c_c c_v n_t;
    datalines;
480 480 30 40 20 8
;
run;

/* Macro to set the number of telehealth nurses */
%let n_t = 20;

/* Use PROC OPTMODEL to solve the problem */
proc optmodel;
    /* Define sets */
    set PATIENTS = 1..10;
    set TELEHEALTH_NURSES = 1..&n_t;
    set TRAVEL_CAREGIVERS = 1..8;
    set VEHICLES = 1..4;

    /* Define parameters */
    number d{PATIENTS};
    number travel_time{PATIENTS, PATIENTS};
    number H_t;
    number H_c;
    number r{PATIENTS};
    number c_t;
    number c_c;
    number c_v;

    /* Read data */
   read data patient_data into [i] d=duration r=revenue;
   read data travel_times_final into [i j] travel_time=t;
   read data nurse_data into H_t H_c c_t c_c c_v;

   /* Define variables */
   var X{PATIENTS, TELEHEALTH_NURSES} binary;
   var Y{PATIENTS, TRAVEL_CAREGIVERS} binary;
   var Z{PATIENTS, PATIENTS, TRAVEL_CAREGIVERS, VEHICLES} binary;
   var U{PATIENTS} integer >= 1 <= card(PATIENTS);

   /* Objective function */
   max Profit = sum{i in PATIENTS} (r[i] * (sum{tn in TELEHEALTH_NURSES} X[i,tn] + 
                sum{c in TRAVEL_CAREGIVERS} Y[i,c]))
                - sum{tn in TELEHEALTH_NURSES} (c_t * sum{i in PATIENTS} d[i] * X[i,tn])
                - sum{c in TRAVEL_CAREGIVERS} (c_c * (sum{i in PATIENTS} d[i] * Y[i,c] + 
                  sum{i in PATIENTS, j in PATIENTS, v in VEHICLES} travel_time[i,j] * Z[i,j,c,v]))
                - sum{v in VEHICLES} (c_v * sum{c in TRAVEL_CAREGIVERS, i in PATIENTS, j in PATIENTS} 
                  travel_time[i,j] * Z[i,j,c,v]);

   /* Constraints */
   con Patient_Assignment{i in PATIENTS}:
       sum{tn in TELEHEALTH_NURSES} X[i,tn] + sum{c in TRAVEL_CAREGIVERS} Y[i,c] = 1;

   con Telehealth_Hours{tn in TELEHEALTH_NURSES}:
       sum{i in PATIENTS} d[i] * X[i,tn] <= H_t;

   con Travel_Caregiver_Hours{c in TRAVEL_CAREGIVERS}:
       sum{i in PATIENTS} d[i] * Y[i,c] + 
       sum{i in PATIENTS, j in PATIENTS, v in VEHICLES} travel_time[i,j] * Z[i,j,c,v] <= H_c;

   con Vehicle_Capacity{v in VEHICLES}:
       sum{c in TRAVEL_CAREGIVERS, i in PATIENTS, j in PATIENTS} Z[i,j,c,v] <= 2;

       
   con Flow_Conservation{i in PATIENTS, c in TRAVEL_CAREGIVERS}:
       sum{j in PATIENTS, v in VEHICLES} Z[i,j,c,v] = Y[i,c];

   con Flow_Conservation_Reverse{i in PATIENTS, c in TRAVEL_CAREGIVERS}:
       sum{j in PATIENTS, v in VEHICLES} Z[j,i,c,v] = Y[i,c];    

   con Subtour_Elimination{i in PATIENTS, j in PATIENTS, c in TRAVEL_CAREGIVERS: i ne j}:
       U[i] - U[j] + 1 <= card(PATIENTS) * (1 - sum{v in VEHICLES} Z[i,j,c,v]);

   con Ordering_Link{i in PATIENTS, c in TRAVEL_CAREGIVERS}:
       U[i] >= 1 + card(PATIENTS) * (Y[i,c] - 1);

   /* Solve the model */
   solve;

   /* Print results */
   print X Y Z U;
quit;
9 REPLIES 9
PaigeMiller
Diamond | Level 26

Please, when you get an error, show us the log, including the code as it appears in the log, and any ERROR or WARNING or NOTE message.

 

If the problem occurs in a specific PROC, just show us the log for that PROC.

 

Please click on the </> icon, paste your log as text (not a screen capture) into the window that appears.

PaigeMiller_0-1715196634946.png

--
Paige Miller
JackieJ_SAS
SAS Employee

I'll second that we do need to see the log to be able to help with this. You mentioned this error message:

ERROR: The array element 'travel_time[1,2]' has no value at line 228 column 57

A search of your program shows that travel_time is used several times, so, without the log, we can't tell which part is causing the issue.

 

The line and column numbers mentioned in the error are referring to notes in the log. For example, say your log looked like this:

 

      
 73         data temp;
 74         set sashelp.heart;
 75         array one{3};
 76         do i=1 to 4;
 77         myar=one[i];
 78         end;
 79         run;
 
 ERROR: Array subscript out of range at line 77 column 6.
 NOTE: The SAS System stopped processing this step because of errors.
 NOTE: There were 1 observations read from the data set SASHELP.HEART.

Line 77 is referring to line 77 in the log (myvar=one[i];), and column 6 is referring to the sixth letter in line 77 (the letter o of one).

 

norachanisara
Calcite | Level 5

Dear Paige and Jackie,

 

Thank you very much for fast response. Here is the log of when I run the code. Please do let me know if I'm not pasting the right thing. I am fairly new to SAS and the community. 

 

 1          OPTIONS NONOTES NOSTIMER NOSOURCE NOSYNTAXCHECK;
 68         
 69         /* Patient data: duration of treatment and revenue */
 70         data patient_data;
 71             input i duration revenue;
 72             datalines;
 
 NOTE: The data set WORK.PATIENT_DATA has 10 observations and 3 variables.
 NOTE: DATA statement used (Total process time):
       real time           0.00 seconds
       user cpu time       0.01 seconds
       system cpu time     0.00 seconds
       memory              666.03k
       OS Memory           19620.00k
       Timestamp           09/17/2024 12:23:14 AM
       Step Count                        24  Switch Count  2
       Page Faults                       0
       Page Reclaims                     136
       Page Swaps                        0
       Voluntary Context Switches        11
       Involuntary Context Switches      0
       Block Input Operations            0
       Block Output Operations           264
       
 
 83         ;
 84         run;
 85         
 86         /* Travel times between patients (symmetric for simplicity) */
 87         data travel_times;
 88             input i j t;
 89             datalines;
 
 NOTE: The data set WORK.TRAVEL_TIMES has 55 observations and 3 variables.
 NOTE: DATA statement used (Total process time):
       real time           0.00 seconds
       user cpu time       0.00 seconds
       system cpu time     0.00 seconds
       memory              666.03k
       OS Memory           19620.00k
       Timestamp           09/17/2024 12:23:14 AM
       Step Count                        25  Switch Count  2
       Page Faults                       0
       Page Reclaims                     91
       Page Swaps                        0
       Voluntary Context Switches        11
       Involuntary Context Switches      0
       Block Input Operations            0
       Block Output Operations           264
       
 
 145        ;
 146        run;
 147        
 148        /* Generate full travel time matrix */
 149        data travel_times_full;
 150            set travel_times;
 151            output;
 152            t_temp = t;
 153            t = t_temp;
 154            i_temp = i;
 155            i = j;
 156            j = i_temp;
 157            output;
 158        run;
 
 NOTE: There were 55 observations read from the data set WORK.TRAVEL_TIMES.
 NOTE: The data set WORK.TRAVEL_TIMES_FULL has 110 observations and 5 variables.
 NOTE: DATA statement used (Total process time):
       real time           0.00 seconds
       user cpu time       0.00 seconds
       system cpu time     0.00 seconds
       memory              947.40k
       OS Memory           19880.00k
       Timestamp           09/17/2024 12:23:14 AM
       Step Count                        26  Switch Count  2
       Page Faults                       0
       Page Reclaims                     122
       Page Swaps                        0
       Voluntary Context Switches        10
       Involuntary Context Switches      0
       Block Input Operations            0
       Block Output Operations           272
       
 
 159        
 160        /* Add diagonal elements (travel time to self = 0) */
 161        data travel_times_final;
 162            set travel_times_full;
 163            do i = 1 to 10;
 164                j = i;
 165                t = 0;
 166                output;
 167            end;
 168        run;
 
 NOTE: There were 110 observations read from the data set WORK.TRAVEL_TIMES_FULL.
 NOTE: The data set WORK.TRAVEL_TIMES_FINAL has 1100 observations and 5 variables.
 NOTE: DATA statement used (Total process time):
       real time           0.00 seconds
       user cpu time       0.00 seconds
       system cpu time     0.00 seconds
       memory              941.93k
       OS Memory           19880.00k
       Timestamp           09/17/2024 12:23:14 AM
       Step Count                        27  Switch Count  2
       Page Faults                       0
       Page Reclaims                     109
       Page Swaps                        0
       Voluntary Context Switches        12
       Involuntary Context Switches      0
       Block Input Operations            0
       Block Output Operations           264
       
 
 169        
 170        /* Nurse and vehicle data */
 171        data nurse_data;
 172            input H_t H_c c_t c_c c_v n_t;
 173            datalines;
 
 NOTE: The data set WORK.NURSE_DATA has 1 observations and 6 variables.
 NOTE: DATA statement used (Total process time):
       real time           0.00 seconds
       user cpu time       0.01 seconds
       system cpu time     0.00 seconds
       memory              668.03k
       OS Memory           19620.00k
       Timestamp           09/17/2024 12:23:14 AM
       Step Count                        28  Switch Count  2
       Page Faults                       0
       Page Reclaims                     85
       Page Swaps                        0
       Voluntary Context Switches        12
       Involuntary Context Switches      0
       Block Input Operations            0
       Block Output Operations           264
       
 
 175        ;
 176        run;
 177        
 178        /* Macro to set the number of telehealth nurses */
 179        %let n_t = 20;
 180        
 181        /* Use PROC OPTMODEL to solve the problem */
 182        proc optmodel;
 183            /* Define sets */
 184            set PATIENTS = 1..10;
 185            set TELEHEALTH_NURSES = 1..&n_t;
 186            set TRAVEL_CAREGIVERS = 1..8;
 187            set VEHICLES = 1..4;
 188        
 189            /* Define parameters */
 190            number d{PATIENTS};
 191            number travel_time{PATIENTS, PATIENTS};
 192            number H_t;
 193            number H_c;
 194            number r{PATIENTS};
 195            number c_t;
 196            number c_c;
 197            number c_v;
 198        
 199            /* Read data */
 200           read data patient_data into [i] d=duration r=revenue;
 NOTE: There were 10 observations read from the data set WORK.PATIENT_DATA.
 201           read data travel_times_final into [i j] travel_time=t;
 WARNING: Duplicate key <1,1> was read at observation 11.
 WARNING: Duplicate key <2,2> was read at observation 12.
 WARNING: Duplicate key <3,3> was read at observation 13.
 WARNING: Duplicate key <4,4> was read at observation 14.
 WARNING: Duplicate key <5,5> was read at observation 15.
 WARNING: Duplicate key <6,6> was read at observation 16.
 WARNING: Duplicate key <7,7> was read at observation 17.
 WARNING: Duplicate key <8,8> was read at observation 18.
 WARNING: Duplicate key <9,9> was read at observation 19.
 WARNING: Duplicate key <10,10> was read at observation 20.
 WARNING: Duplicate key <1,1> was read at observation 21.
 WARNING: Duplicate key <2,2> was read at observation 22.
 WARNING: Duplicate key <3,3> was read at observation 23.
 WARNING: Duplicate key <4,4> was read at observation 24.
 WARNING: Duplicate key <5,5> was read at observation 25.
 WARNING: Duplicate key <6,6> was read at observation 26.
 WARNING: Duplicate key <7,7> was read at observation 27.
 WARNING: Duplicate key <8,8> was read at observation 28.
 WARNING: Duplicate key <9,9> was read at observation 29.
 WARNING: Duplicate key <10,10> was read at observation 30.
 WARNING: Duplicate key <1,1> was read at observation 31.
 WARNING: Duplicate key <2,2> was read at observation 32.
 WARNING: Duplicate key <3,3> was read at observation 33.
 WARNING: Duplicate key <4,4> was read at observation 34.
 WARNING: Duplicate key <5,5> was read at observation 35.
 NOTE: 1090 duplicate keys were read.
 NOTE: There were 1100 observations read from the data set WORK.TRAVEL_TIMES_FINAL.
 NOTE: The maximum message limit was reached during execution of the statement block. 1065 notes and warnings were not displayed.
 202           read data nurse_data into H_t H_c c_t c_c c_v;
 NOTE: There were 1 observations read from the data set WORK.NURSE_DATA.
 203        
 204           /* Define variables */
 205           var X{PATIENTS, TELEHEALTH_NURSES} binary;
 206           var Y{PATIENTS, TRAVEL_CAREGIVERS} binary;
 207           var Z{PATIENTS, PATIENTS, TRAVEL_CAREGIVERS, VEHICLES} binary;
 208           var U{PATIENTS} integer >= 1 <= card(PATIENTS);
 209        
 210           /* Objective function */
 211           max Profit = sum{i in PATIENTS} (r[i] * (sum{tn in TELEHEALTH_NURSES} X[i,tn] +
 212                        sum{c in TRAVEL_CAREGIVERS} Y[i,c]))
 213                        - sum{tn in TELEHEALTH_NURSES} (c_t * sum{i in PATIENTS} d[i] * X[i,tn])
 214                        - sum{c in TRAVEL_CAREGIVERS} (c_c * (sum{i in PATIENTS} d[i] * Y[i,c] +
 215                          sum{i in PATIENTS, j in PATIENTS, v in VEHICLES} travel_time[i,j] * Z[i,j,c,v]))
 216                        - sum{v in VEHICLES} (c_v * sum{c in TRAVEL_CAREGIVERS, i in PATIENTS, j in PATIENTS}
 217                          travel_time[i,j] * Z[i,j,c,v]);
 218        
 219           /* Constraints */
 220           con Patient_Assignment{i in PATIENTS}:
 221               sum{tn in TELEHEALTH_NURSES} X[i,tn] + sum{c in TRAVEL_CAREGIVERS} Y[i,c] = 1;
 222        
 223           con Telehealth_Hours{tn in TELEHEALTH_NURSES}:
 224               sum{i in PATIENTS} d[i] * X[i,tn] <= H_t;
 225        
 226           con Travel_Caregiver_Hours{c in TRAVEL_CAREGIVERS}:
 227               sum{i in PATIENTS} d[i] * Y[i,c] +
 228               sum{i in PATIENTS, j in PATIENTS, v in VEHICLES} travel_time[i,j] * Z[i,j,c,v] <= H_c;
 229        
 230           con Vehicle_Capacity{v in VEHICLES}:
 231               sum{c in TRAVEL_CAREGIVERS, i in PATIENTS, j in PATIENTS} Z[i,j,c,v] <= 2;
 232        
 233        
 234           con Flow_Conservation{i in PATIENTS, c in TRAVEL_CAREGIVERS}:
 235               sum{j in PATIENTS, v in VEHICLES} Z[i,j,c,v] = Y[i,c];
 236        
 237           con Flow_Conservation_Reverse{i in PATIENTS, c in TRAVEL_CAREGIVERS}:
 238               sum{j in PATIENTS, v in VEHICLES} Z[j,i,c,v] = Y[i,c];
 239        
 240           con Subtour_Elimination{i in PATIENTS, j in PATIENTS, c in TRAVEL_CAREGIVERS: i ne j}:
 241               U[i] - U[j] + 1 <= card(PATIENTS) * (1 - sum{v in VEHICLES} Z[i,j,c,v]);
 242        
 243           con Ordering_Link{i in PATIENTS, c in TRAVEL_CAREGIVERS}:
 244               U[i] >= 1 + card(PATIENTS) * (Y[i,c] - 1);
 245        
 246           /* Solve the model */
 247           solve;
 NOTE: Problem generation will use 2 threads.
 ERROR: The array element 'travel_time[1,2]' has no value at line 228 column 57.
 ERROR: The array element 'travel_time[1,2]' has no value at line 228 column 57.
 NOTE: Unable to create problem instance due to previous errors.
 248        
 249           /* Print results */
 250           print X Y Z U;
 251        quit;
 NOTE: The SAS System stopped processing this step because of errors.
 NOTE: PROCEDURE OPTMODEL used (Total process time):
       real time           1.61 seconds
       user cpu time       1.59 seconds
       system cpu time     0.01 seconds
       memory              3191.06k
       OS Memory           22456.00k
       Timestamp           09/17/2024 12:23:16 AM
       Step Count                        29  Switch Count  5
       Page Faults                       0
       Page Reclaims                     1146
       Page Swaps                        0
       Voluntary Context Switches        52
       Involuntary Context Switches      3
       Block Input Operations            0
       Block Output Operations           1816
       
 252        
 253        
 254        
 255        OPTIONS NONOTES NOSTIMER NOSOURCE NOSYNTAXCHECK;
 265        
Ksharp
Super User

From your LOG:

200           read data patient_data into [i] d=duration r=revenue;
 NOTE: There were 10 observations read from the data set WORK.PATIENT_DATA.
 201           read data travel_times_final into [i j] travel_time=t;
 WARNING: Duplicate key <1,1> was read at observation 11.
 WARNING: Duplicate key <2,2> was read at observation 12.
 WARNING: Duplicate key <3,3> was read at observation 13.
 WARNING: Duplicate key <4,4> was read at observation 14.

That imply your INDEX variable PATIENTS

 travel_time{PATIENTS, PATIENTS};  

 have duplicated values as showed in following picture:

Ksharp_1-1726535414350.png

 

Due to index variable can not have duplicated values ,you either using a DO LOOP to read it in one by one or make a unique index value to read it all .

PaigeMiller
Diamond | Level 26

@norachanisara wrote:

Dear Paige and Jackie,

 

Thank you very much for fast response. Here is the log of when I run the code. Please do let me know if I'm not pasting the right thing. I am fairly new to SAS and the community. 

Please read carefully. I said: "If the problem occurs in a specific PROC, just show us the log for that PROC."

--
Paige Miller
RobPratt
SAS Super FREQ

Your DATA steps lost some of the data.  Here's a simpler approach, just reading from the original travel_times data:

/*   read data travel_times_final into [i j] travel_time=t;*/
   read data travel_times into [i j] travel_time=t;
   for {i in PATIENTS} travel_time[i,i] = 0;
   for {i in PATIENTS, j in PATIENTS: travel_time[i,j] = _NIL_} travel_time[i,j] = travel_time[j,i];
   print travel_time;
norachanisara
Calcite | Level 5

Thank you very much Rob. I have encountered this problem quite a few times. Would you recommend inputting distance data directly as a matrix?

 

for example

num d{P,P} = [

0  42.00  44.159  23.43  41.38
42.00  0  3.50  18.70  0.76
44.15  3.50  0  21.17  3.58
23.43  18.70  21.17  0  18.13
41.38  0.76  3.58  18.13  0

];

RobPratt
SAS Super FREQ

That is another valid approach but is a bit error-prone.  For example, are the 44.159 and 44.15 supposed to be the same?