Skip to Content
Product Information
Author's profile photo Thomas Engelmann

Effective optimization: Enhancement – create your own world for optimization

As you may know we use Meta-Heuristic for our VSR-optimization. We call it evolutionary local search. One important part in such an approach are the local steps to check every possibility in a neighborhood and some random steps to get new aspects into your plans. But beside of that it is very important we have very efficient steps to construct the transportation plans. That means we have to exploit all the information of our data and to concentrate on that kind of plans which are usual rated as good or very good.

Because of that our algorithms inside VSR are highly sophisticated. They are created and adapted to the feature-set of TM and what we learned from our customers about good transportation plans.

If you now want to change that behavior of it, to support new features, constraints or cost functions, it would be no good idea, to just do a minimal change and add this feature or constraint. As long as you don’t adapt the constructions step, so that your kind of wanted plan becomes possible, the optimizer would not work efficiently. Without deeper changes the algorithms would still try to construct the same plans like before. Adding new cost functions to express what is expected are required, that the engine can decide, when a plan is better than another. But much more painful: All the algorithms for construction have to be adapted. Otherwise they would destroy the new wanted feature of the plan directly in the next step after they have found it.

That means enhancing the algorithms to get a new behavior can be cumbersome and expensive. But there is another possibility, which helps in a lot of requirements: We change the data instead of the algorithm

Let’s look what’s happening, if we call the optimizer: The application is reading all data which is required for the optimization run. It collects all this data and sends it in one large package to the optimizer. After the optimizer has found its solution, we have the same into the other direction: The optimizer sends back the transportation plan und explanations to the TM system, which is saving these results during the post-processing.


As the data are transferred from the application server to the optimizer and back, we have a copy of the data.  A copy implies, that we can change the copied data without changing the TM-system itself. For example you can delete objects in the optimizer data set, without deleting these objects inside TM.

We introduced the BADI /SCMTMS/PLN_OPT to allow such manipulations to the data, which are send to or from the optimizer engine. The BAdI is running on the application server. It is a usual ABAP-BAdI, whereas the optimizer itself is written in C++.
The BAdI has two methods: After the pre-processing you can manipulate the input data for the optimization engine. After optimization you can manipulate the results of the optimizer, before saving it into the TM system.


Like you can see in the drawing above, the BAdII call for transforming the input data and manipulating the result, are inside the calls of the explanation tool. This means

  • If you manipulate the input data, you see the original input data in the explanation tool. You don’t see your manipulation
  • In upload stop you can write additional information into the explanation, to write details about your changes to the objects.
  • In general you can see the BAdI as part of the optimization process. Whereas the explanation tool describes the state before and after optimization and BAdI.

Let’s have a look, on what you can do with the BAdI: The simplest usage is the deletion of some constraints. There are already several parameters in the planning profile, which you can use to disable some constraints. But these switches work on a general level. If you want to ignore or modify some but not all constraints of one type you can do it with the BAdI.

  • Ignoring or modifying of you dates, acceptable or requested dates on Freight Units
  • Capacities of trucks, trailers, compartments bookings or schedules.
  • Changing of distances or durations to overwrite the general geo information

Whereas the examples above manipulate the input data for the optimizer, it is also valid to change the results:

  • You can delete specific Freight Orders or Bookings, if they don’t satisfy your expectations, for example if the utilization is too low.

One of the most important data to the optimizer is the transportation network. Especially if you want to keep it simple for the maintenance and manual planning, but you want to have some more complex effect inside your automatic planning you can do that in the BAdI, too:

  • In the blog about simple networks I introduced a modelling to enforce that some locations are the first delivery locations on tours. Instead of a persistent modelling like in the blog you can transform your network on the fly when calling the optimizer.
  • So far the optimizer cannot handle via-locations. You can add them in the BAdI, if you add the additional duration, distance and cost in the distance table. This guides the optimizer engine too consider the additional effort to go via the via-location.
    In the result of the optimizer you add this via-location whenever such a distance is selected.

One very common usage of the engine is to add data which are not yet maintainable inside TM into the optimization process. In some special areas we have the situation, that the optimizer already supports functionality, which is not supported in TM application:

  • Ship-With-Groups
    The optimizer can respect groups of FU-stages which should be planned together in one common Freight Order. You can find Details in this note.
  • Cost-Model
    The optimizer has a sophisticated model for cost on bookings and schedules. Currently only very basic cost rates are transferred to the optimization engine.
  • Sustainability
    The engine has features to reduce the carbon emissions. The can be handled like additional costs.

You see, there a lot of different possibilities to adapt the engine via the data to your scenarios. In principal we can see, this is quite simple, as long as you only change some values, or delete some constraints in the input data.
As soon as you introduce new objects into the input of the optimizer, these new objects may become part of the solution. Then you have to do the mapping into the objects of your TM system after the optimization,too.

In some cases the required new behavior, cannot be implemented vie the BAdI. You might need to change the behavior of the optimization engine itself. For example, to create somehow different transportation plans or to add a new cost function to evaluate plans. In these cases it’s often not enough to change only the data. We have to adapt the logic and the coding of the optimizer.
If you expect to need such a change inside the optimizer engine, you should contact our expert consulting first. They can give you hints how other users solved similar requirements or if there was a similar enhancement done already. If there is no such mitigation, you have to think about a customer development project. There are experts in our department for customer developments, which are specialized to the optimizer and will find fast and efficient solutions to utilize this BAdI for your extensions.

Assigned Tags

      You must be Logged on to comment or reply to a post.
      Author's profile photo Former Member
      Former Member


      This is a wonderful post and we use the ship with group in the pre-optimizer badi.  Also we have created a Z-table which is referenced while sending the network data to optimizer.

      One thing that we could not do is the distance between the stops.  When the optimizer is building multi stop Truck Load FOR's we do not want any stop more than 400 miles.  Is it possible to achieve this in the pre-optimizer badi. 

      Thanks and Regards,


      Author's profile photo Thomas Engelmann
      Thomas Engelmann
      Blog Post Author

      Hi Suresh!

      There are two possibilities to set a 400-miles-limit:

      • In the profile for planning cost you can define a maximal limit for the distance of Freight Orders. This restricts all FORs to less distance. You have to define it per Means-of-Transport.
      • If you do it inside the BAdI, you have to manipulate the entries in the table ET_DISTANCE_GISCOORD. If an entry is larger than your limit, you set a higher value for duration and distance, so that it is no longer an interesting alternative for the engine. This allows larger FOR's, but every stage is restricted by your limit.
        doing so yuo must be very careful: If the value itself would violate any limits, the optimizer is no longer able to produce such solutions. But it might be to optimizer needs exactly this possibility to construct an intermediate solution, for example to come back to the depot or to reach a swap-point for trailers.
        Usually it is the best way to change the value only a little bit, so that it is no longer interesting from a cost point of view, but still a feasible solution.

      Best Regards, Thomas

      Author's profile photo Former Member
      Former Member

      Hi Tom,

      For us the maximum distance traveled by FOR does not makes more sense.  Since in our scenario, the first stop is ok to have maximum distance but the trucking company hesitate to take the loads when there are intermediate stops getting created with distance more than 400 miles.

      We debugged the pre-optimizer BADI and elevated the distance in distance_giscord table and Optimizer did not put a multi stop load and this works our for us. 🙂   Thanks for your inputs.

      Thanks and Regards,


      Author's profile photo Former Member
      Former Member

      There are many trickiest options that are available in this pre-optimizer badi and it is very interesting to know these can change the way the optimizer works.  Kudos to Thomas.

      Author's profile photo B. Mateman
      B. Mateman

      Dear Thomas,

      Thanks for this useful information, maybe it can help to solve the requirement of our customer.

      Currently the customer has for example 10 identical trucks(resources) of the same type with the same costs in the system. These reside all at the same location. So basically it doesn't matter which of these resource is used to transport a freightunit(s). However the optimizer always assigns the freightunit(s) to the first available truck in the database. As a consequence truck number 1 has got a very high mileage and truck number 10 a very low mileage. So the customer is looking for a solution that random selects the resource, if there is more than 1 resource available with same low costs.

      Do you think this Badi might be a good solution?

      With kind regards,


      Author's profile photo Thomas Engelmann
      Thomas Engelmann
      Blog Post Author

      Hello Beno!

      Yes, you can solve the requirement with the Badi. Either you doe a sequencing of the resources, when they are sent to the optimization engine, or you change the resource in the result of the optimization.

      So far we plan no balanced resource selection inside the engine, so the Badi is the preferred way to do it.

      Best Regards,


      Author's profile photo Jordi Alarcón Gómez
      Jordi Alarcón Gómez

      Hi Thomas, how are you??

      We have a very usual requirement that SAP TM can´t resolve it in standard form, and I would like whether you can help us to think the best way (using pre-optimizer BADI or any Advanced Parameter in RCC_PARAM) to face it.

      The customer needs that the VSR Optimizer takes into account delivery priorities of FU´s. Basically, the FUs with highest priorities should be planned before than FUs with a low prority, everything in one VSR run.

      For example:

      • 1 Resource with 30 TO of Capacity
      • 1 FU(FU-A) with Delivery Priority = 1 (highest) and weight = 30 TO
      • 1 FU(FU-B) with Delivery Priority = 2 and weight = 30 TO

      So, the necessary result for this case is:

      • FO 1 (day 1) –> 1 FU (A) –> Load Weigth= 30 TO
      • FO 2 (day 2) –> 1 FU (B) –> Load Weigth= 30 TO


      Another example:

      • 1 Resource with 30 TO of Capacity
      • 1 FU(FU-A) with Delivery Priority = 1 (highest) and weight = 20 TO
      • 2 FU(FU-B y FU-C) with Delivery Priority = 2 and weight = 10 TO (each one)

      The behavior using SHIP_WITH grouping by Prority is that the VSR creates 2 FOs:

      • FO 1 (day 1) –> 1 FU (A) –> Load Weigth= 20TO
      • FO 2 (day 2) –> 1 FU (B and C) –> Load Weigth= 20TO

      Nevertheless, we need that the system create the plan in the following way:

      • FO 1 –> 1 FU (A, and B or C) –> Load Weigth= 30 TO
      • FO 2 –> 1 FU (B or C) –> Load Weigth= 10 TO


      In previous examples we had consider the following assumptions:

      • All FUs has the same TW.
      • All FUs has the same Origin and Destination.

      Another option that we are thinking about is that the Pre-Optimizer BADI changes the dates of the FUs, making the FU with more priority have an earlier date or time, and therefore, more delay costs. This would be complex because many business cases such as FU with dates in the past or in the distant future must be included in the scope.

      What do you think? Is there another option to handling Delivery Priorities in VSR Optimizer?

      Thanks a lot!!

      Best Regards

      Author's profile photo Whelton Jose de Andrade
      Whelton Jose de Andrade
      Dear Thomas,
      We are implementing the BADI ENH_PLN_PRE_PROC
      to eliminate specific UFs by the client process, before sending to the optimizer you would have a hint of which structure
      can we use to eliminate these FUs? 

      Thanks a lot!!

      Best Regards



      Author's profile photo Wolfgang Barheine
      Wolfgang Barheine

      Dear Whelton,

      Table ET_TOR contains the root entries of all freight units and other so-called TOR-based objects (e.g. freight orders).
      Locate the table entries of the FUs you want to exclude from planning and clear the field RELEVANT (i.e. set it to space).
      The effect will be that the optimizer leaves the corresponding FUs untouched.
      Please note: If the FUs you want to exclude from planning have already been planned before, then setting them to irrelevant causes fixations of related objects like the freight orders they were assigned to.
      Have look at the explanation tool to check if such side effects occurred.

      Best regards,

      Author's profile photo Whelton Jose de Andrade
      Whelton Jose de Andrade

      Dear Wolfgang,

      We found the point where it comments.

      Inside the BADI SCMTMS/PLN_PRE_PROC there is the method /SCMTMS/IF_PLN_PRE_PROC~CHANGE_OPT_INPUT and inside it the variable IO_OPT_INPUT->MT_ET_TOR where we cleared the RELEVANT field and it worked!

      Thank you Wolfgang for the contribution!