Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    text
    copied!<p>You might just reuse this <a href="https://stackoverflow.com/questions/17112494/how-to-expand-environment-variables-in-ini-files-using-boost/17128601#17128601">c++ solution</a> (replacing the generic iterators by hardcoding <code>char*</code> instead).</p> <p>I gave it a whirl. However, I wish to give a warning: it looks like you're trying to implement an expression parser. I'd strongly advise you to either</p> <ul> <li>handroll a (recursive descent) parser</li> <li>use flex/bison (or lex/yacc)</li> </ul> <p>so you don't paint yourself in an awkward corner of error-prone text-handling in C.</p> <blockquote> <h3><strong>Edit:</strong> I rewrote <a href="http://pastebin.com/AgcDi7YU" rel="nofollow noreferrer">your C program</a> using C++; you can see it <a href="http://coliru.stacked-crooked.com/view?id=814ec79f83fa4d93a9be9f5500988b50-0681a6d6fa3348403a2b0d4989bfddf5" rel="nofollow noreferrer">working live here</a>.</h3> <h3><strong>Edit 2:</strong> Another fixup of your C program in pure C: <strong><a href="http://ideone.com/ExnufJ" rel="nofollow noreferrer">http://ideone.com/ExnufJ</a></strong> <em>updated to support iterative expansions now, too</em></h3> </blockquote> <p>The answer just concerns itself with the pure C approach:</p> <p>So, let's get started. I assumed a sample "spreadsheet" (it could contain numbers instead of strings):</p> <pre><code>const char* cells[][4] = { /* A B C D */ { "the" , "lazy" , "cow" , "jumped" }, /* 1 */ { "over" , "the" , "quick", "brown" }, /* 2 */ { "paper", "packages", "tied" , "up" }, /* 3 */ { "with" , "silver" , "white", "winters" }, /* 4 */ { "that" , "melt" , "fox" , "springs" }, /* 5 */ }; </code></pre> <p>Using just two helpers:</p> <pre><code>const char* get_cell_value(const char* coordinate_b, const char* coordinate_e); char* expand_cell_references(const char* f, const char* const l, char* o); /*the magic engine*/ </code></pre> <p>we can write the following demo program:</p> <pre><code>int main() { const char in[] = "The C2 D2 C5 D1 A2 B2 B1 dog!"; char out[1024] = {0}; expand_cell_references(in, in+strlen(in), out); puts(out); /* "The quick brown fox jumped over the lazy dog!" */ return 0; } </code></pre> <p>which prints the well-known test phrase as per the comment. Now, <code>get_cell_value</code> is really simple:</p> <pre><code>const char* get_cell_value(const char* coordinate_b, const char* coordinate_e) { size_t col = 0, row = 0; const char* it; for (it=coordinate_b; it != coordinate_e; ++it) { if (*it &gt;= 'A' &amp;&amp; *it &lt;= 'Z') col = 26*col + (*it - 'A'); if (*it &gt;= '0' &amp;&amp; *it &lt;= '9') row = 10*row + (*it - '0'); /* or use atoi and friends */ } row--; /* 1-based row nums in Excel */ return cells[row][col]; /* 1-based indexes in Excel */ } </code></pre> <p>And <code>expand_cell_references</code> is slightly more involved, being a simple DFA parser:</p> <pre><code>char* expand_cell_references(const char* f, const char* const l, char* o) { enum parser_state { other, in_coord_col, in_coord_row } state = other; /*temporary storage for coordinates being parsed:*/ char accum[16] = {0}; char* accit = accum; while (f!=l) { switch(state) /*dummy, the transitions flow in fallthrough order for now*/ { case other: *(accit = accum) = 0; /*reset the accumulator*/ while (f!=l &amp;&amp; !(*f&gt;='A' &amp;&amp; *f&lt;='Z')) *o++ = *f++; /*fallthrough*/ case in_coord_col: while (f!=l &amp;&amp; *f&gt;='A' &amp;&amp; *f&lt;='Z') *accit++ = *f++; /*fallthrough*/ case in_coord_row: { const char* expanded = accum; if (f!=l &amp;&amp; *f&gt;='0' &amp;&amp; *f&lt;='9') { while (f!=l &amp;&amp; *f&gt;='0' &amp;&amp; *f&lt;='9') *accit++ = *f++; expanded = get_cell_value(accum, accit); } else { *accit = 0; } while (*expanded) *o++ = *expanded++; continue; /*state = other;*/ } } } return o; } </code></pre> <p>I took some shortcuts there, because this grammar is so minimalist, but it should give you a proper idea of where to start.</p> <blockquote> <p>See a live demo here <strong><a href="http://ideone.com/kS7XqB" rel="nofollow noreferrer">http://ideone.com/kS7XqB</a></strong> so you can play with it yourself. Note that I added debugging (asserts) to the <code>get_cell_value</code> function so you don't accidentally reference out-of-bounds indexes.</p> </blockquote>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload