I would like to transform the following list:

data = {{0, A1, 1}, {1, C1, 2}, {1, C2, 3}, {3, C4, 1}, {0, A2, 1}, {1, C2, 1},
{0, A1, 4}, {1, C1, 1}, {2, C2, 1}}


into another list like this:

output = {{A1, 1, 0, A1, 1}, {A1, 1, 1, C1, 2}, {A1, 1, 1, C2, 3}, {A1, 1, 3, C4, 1},
{A2, 1, 0, A2, 1}, {A2, 1, 1, C2, 1}, {A1, 4, 0, A1, 4}, {A1, 4, 1, C1, 1},
{A1, 4, 2, C2, 1}}


Basically, the first column indicates the level, 0 being the head level of a bill of material and would like to put the header item and header quantity as columns besides the components for easier computation further along.

Thanks.

-

The first thing you should do is collect all the elements under a single header into their own sublists. Assuming the "levels" are always in increasing order, this will do the job:

sublists = Split[data, First@#1 <= First@#2 &]
(* {{{0, A1, 1}, {1, C1, 2}, {1, C2, 3}, {3, C4, 1}},
{{0, A2, 1}, {1, C2, 1}},
{{0, A1, 4}, {1, C1, 1}, {2, C2, 1}}} *)


Then for each sublist, you can just take its header and join it to all its elements.

formatted = Function[list, Join[Rest@First@list, #] & /@ list] /@ sublists
(* {{{A1, 1, 0, A1, 1}, {A1, 1, 1, C1, 2}, {A1, 1, 1, C2, 3}, {A1, 1, 3, C4, 1}},
{{A2, 1, 0, A2, 1}, {A2, 1, 1, C2, 1}},
{{A1, 4, 0, A1, 4}, {A1, 4, 1, C1, 1}, {A1, 4, 2, C2, 1}}} *)


In the end you probably also want to flatten the sublists.

output = Flatten[formatted, 1]
(* {{A1, 1, 0, A1, 1}, {A1, 1, 1, C1, 2}, {A1, 1, 1, C2, 3}, {A1, 1, 3, C4, 1},
{A2, 1, 0, A2, 1}, {A2, 1, 1, C2, 1}, {A1, 4, 0, A1, 4}, {A1, 4, 1, C1, 1},
{A1, 4, 2, C2, 1}} *)


Of course, all of this can be pulled into a single expression if you prefer:

output = Flatten[
Function[list, Join[Rest@First@list, #] & /@ list] /@
Split[data, First@#1 <= First@#2 &], 1]

-

Guessing the "header" data from the two lists in your question, and making non-numeric elements strings,

data = {{0, "A1", 1}, {1, "C1", 2}, {1, "C2", 3}, {3, "C4", 1}, {0,"A2", 1},
{1, "C2", 1}, {0, "A1", 4}, {1, "C1", 1}, {2, "C2", 1}};
headers = {{"A1", 1}, {"A1", 1}, {"A1", 1}, {"A1", 1}, {"A2", 1}, {"A2", 1},
{"A1", 4}, {"A1", 4}, {"A1", 4}};


you can use

MapThread[Join, {headers, data}];
(* or *)  Transpose[Flatten[Transpose /@ {headers, data}, 1]]


All give

{{"A1", 1, 0, "A1", 1}, {"A1", 1, 1, "C1", 2}, {"A1", 1, 1, "C2", 3},
{"A1", 1, 3, "C4", 1}, {"A2", 1, 0, "A2", 1}, {"A2", 1, 1, "C2", 1},
{"A1", 4, 0, "A1", 4}, {"A1", 4, 1, "C1", 1}, {"A1", 4, 2, "C2", 1}}

-
I think the header is supposed to be the latest entry with first element 0. – Rahul Nov 3 '12 at 7:43
@Rahul, I think you are right ... and that makes it a much more interesting question. – kglr Nov 3 '12 at 8:58
@Rojo/@kgluger/@Rahul, thanks so much for taking a stab at the problem. Just to give some context, the toy problem below is an overall simplification of importing and processing some ascii dumps of 200+ report. In the files you would have a header structure, and then a list of variable number components, header and components with each with its own field structure. I was successful in manipulating the files and dumping everything into a single list and this is where I got stuck. It is still very difficult for me to get away from procedural language structure, – Zviovich Nov 3 '12 at 13:27
which is what I finally used to get things done quickly, but I want to avoid the use of do's and for's in Mathematica. – Zviovich Nov 3 '12 at 13:29

If what @kguler interpreted is correct, then you could do

Rest@FoldList[
Join[If[First@#2 == 0, Rest@#2, #1~Take~2], #2] &, {Null, "Default", Indeterminate},
data]

-