How to create a poly line that fills below (WPF) - wpf

I'm experimenting with shapes in C#/WPF. In a window I create a Polyline with some Points assigned to it:
<Window x:Class="PolylineTest.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<Window.Resources>
<Style TargetType="Polyline">
<Setter Property="SnapsToDevicePixels" Value="True"/>
<Setter Property="Margin" Value="20"/>
</Style>
</Window.Resources>
<Grid>
<Polyline Fill="Red" Stroke="Black" StrokeThickness="2"
FillRule="Nonzero" Points="1, 99 2, 99 3, 99 4, 99 5, 99
6, 99 7, 99 8, 99 9, 98 10, 98 11, 98 12, 98 13, 98 14, 98
15, 98 16, 98 17, 98 18, 98 19, 98 20, 97 21, 96 22, 96
23, 96 24, 96 25, 96 26, 96 27, 96 28, 96 29, 96 30, 96
31, 96 32, 95 33, 96 34, 94 35, 94 36, 94 37, 93 38, 93
39, 94 40, 93 41, 92 42, 93 43, 92 44, 91 45, 91 46, 91
47, 90 48, 89 49, 88 50, 87 51, 86 52, 85 53, 85 54, 83
55, 83 56, 84 57, 86 58, 86 59, 85 60, 85 61, 83 62, 81
63, 77 64, 80 65, 83 66, 78 67, 80 68, 77 69, 72 70, 78
71, 74 72, 76 73, 80 74, 78 75, 81 76, 78 77, 74 78, 73
79, 71 80, 73 81, 67 82, 74 83, 77 84, 73 85, 71 86, 74
87, 74 88, 71 89, 72 90, 72 91, 76 92, 72 93, 67 94, 68
95, 71 96, 72 97, 73 98, 73 99, 74 100, 76 101, 76 102, 77
103, 74 104, 78 105, 77 106, 69 107, 68 108, 68 109, 65
110, 73 111, 71 112, 73 113, 76 114, 66 115, 66 116, 72
117, 73 118, 73 119, 77 120, 73 121, 73 122, 75 123, 77
124, 73 125, 76 126, 79 127, 74 128, 72 129, 74 130, 76
131, 73 132, 76 133, 76 134, 70 "/>
</Grid>
</Window>
This gives the following output:
But what I want to achieve is that only the area below the polyline is filled. Like this:
Using the FillRuleproperty is not helpful here. Is there any way to do it (with polyLine) ?

You may want to draw a filled Path element below the non-filled Polyline, where the Path's Data contains a Geometry that includes the points from the Polyline plus the desired corner points:
<Canvas Margin="20">
<Path Fill="Red">
<Path.Data>
<PathGeometry>
<PathFigure StartPoint="1,100">
<PolyLineSegment Points="{Binding Points, ElementName=polyline}"/>
<LineSegment Point="134,100"/>
</PathFigure>
</PathGeometry>
</Path.Data>
</Path>
<Polyline x:Name="polyline"
Stroke="Black" StrokeThickness="2" StrokeLineJoin="Round"
StrokeStartLineCap="Round" StrokeEndLineCap="Round"
Points="1,99 .. 134,70"/>
</Canvas>

Related

In Golang how can you convert [32]byte to uint64 and then reverse back to [32]byte

I thought I had a good option with the binary package.
but My32ByteArray does not equal Restored32ByteArray
My32ByteArray := []byte{202, 79, 31, 160, 8, 87, 74, 158, 67, 245, 189, 58, 2, 168, 77, 65, 5, 53, 99, 81, 216, 156, 41, 36, 248, 179, 206, 111, 178, 71, 225, 77}
Restored32ByteArray :=[]byte{0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}
TheUint64 = binary.BigEdian.Uint64(My32ByteArray)
binary.BigEdian.PutUint64(Restored32ByteArray, TheUint64)
It does work for the first 8 bytes but the rest of the byte array is left at zeros
I get the following 32byte array
202 79 31 160 8 87 74 158 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
Is there a way to use binary package for this or is it limited to 8 byte arrays or is there another way that will work for this?

How to convert ArrayBuffer to blob so it can be converted to URL for video playback

I'm trying to create a React.js app that can record short video clips, store them in MongoDB, then retrieve those clips from Mongo at another time and playback for the user. I'm able to record video using the react-video-recorder which returns a videoBlob after recording. This videoBlob can be converted via URL.createObjectUrl and set to the src attribute in the HTML video tag. In this case, the video plays back just fine.
However...
If I store this videoBlob in MongoDB, it's converted into a BSON document which contains an ArrayBuffer element in the following format.
ArrayBuffer {
[Uint8Contents]: <1a 45 df a3 9f 42 86 81 01 42 f7 81 01 42 f2 81 04 42 f3 81 08 42 82 84 77 65 62 6d 42 87 81 04 42 85 81 02 18 53 80 67 01 ff ff ff ff ff ff ff 15 49 a9 66 99 2a d7 b1 83 0f 42 40 4d 80 86 43 68 72 6f 6d 65 57 41 86 43 68 72 6f 6d 65 16 54 ae 6b ea ae bd d7 81 01 73 c5 87 2a 21 fb 84 af c3 05 83 81 ... 86733 more bytes>,
byteLength: 86833
}
Here's how the same ArrayBuffer appears when console.logged in the browser:
(86833) [26, 69, 223, 163, 159, 66, 134, 129, 1, 66, 247, 129, 1, 66, 242, 129, 4, 66, 243, 129, 8, 66, 130, 132, 119, 101, 98, 109, 66, 135, 129, 4, 66, 133, 129, 2, 24, 83, 128, 103, 1, 255, 255, 255, 255, 255, 255, 255, 21, 73, 169, 102, 153, 42, 215, 177, 131, 15, 66, 64, 77, 128, 134, 67, 104, 114, 111, 109, 101, 87, 65, 134, 67, 104, 114, 111, 109, 101, 22, 84, 174, 107, 234, 174, 189, 215, 129, 1, 115, 197, 135, 42, 33, 251, 132, 175, 195, 5, 131, 129, …]
[0 … 9999]
[10000 … 19999]
[20000 … 29999]
[30000 … 39999]
[40000 … 49999]
[50000 … 59999]
[60000 … 69999]
[70000 … 79999]
[80000 … 86832]
length: 86833
I haven't been able to successfully convert this ArrayBuffer back into the original blob which can be used to play back the video. How would I go about doing this? Here is what I've already tried:
var returnedArrayBuffer = video.data;//extracting the ArrayBuffer element from BSON document
console.log(returnedArrayBuffer);
var newVideoBlob = new Blob([returnedArrayBuffer], { type: 'video/webm;codecs="vp8,opus"' });//have also tried with a type of just "video/webm", original videoBlob MIME type is exactly as defined here as well
console.log(newVideoBlob);
var url = URL.createObjectURL(newVideoBlob);
However, this returns a blob that is roughly three times the size of the original blob and fails to playback at all. What am I doing wrong here? Any assistance is greatly appreciated.

How to extract a pattern from string containing binary data

I have this array that comes from a previous a=array.unpack("C*") command.
a = [9, 32, 50, 53, 56, 53, 57, 9, 73, 78, 70, 79, 9, 73, 78, 70, 79, 53, 9,
32, 55, 52, 32, 50, 51, 32, 48, 51, 32, 57, 50, 32, 48, 48, 32, 48, 48, 32,
48, 48, 32, 69, 67, 32, 48, 50, 32, 49, 48, 32, 48, 48, 32, 69, 50, 32, 48,
48, 32, 55, 55, 9, 0, 0, 0, 0, 1, 12, 1, 0, 0, 0, 57, 254, 70, 6, 1, 6, 0, 3,
0, 3, 198, 0, 2, 198, 31, 147, 23, 0, 226, 7, 12, 17, 18, 56, 55, 3, 101, 1,
1, 0, 134, 7, 145, 5, 148, 37, 150, 133, 241, 135, 5, 22, 109, 145, 53, 38,
171, 4, 3, 2, 6, 192, 173, 22, 160, 20, 48, 18, 6, 9, 42, 134, 58, 0, 137, 97,
58, 1, 0, 164, 5, 48, 3, 129, 1, 7, 225, 16, 2, 1, 1, 4, 11, 9, 1, 10, 10, 6,
2, 19, 105, 145, 103, 116, 226, 35, 48, 3, 194, 1, 242, 48, 3, 194, 1, 241, 48,
3, 194, 1, 246, 48, 3, 194, 1, 245, 48, 3, 194, 1, 244, 48, 3, 194, 1, 243, 48,
3, 194, 1, 247, 177, 13, 10, 1, 1, 4, 8, 10, 6, 2, 19, 105, 145, 103, 116, 0, 0,
42, 3, 0, 0, 48, 48, 48, 48, 48, 48, 48, 50, 9, 82, 101, 99, 101, 105, 118, 101,
9, 50, 51, 9, 77, 111, 110, 32, 32]
when I convert to chr it looks like this:
irb(main):4392:0> a.map(&:chr).join
=> "\t 25859\tINFO\tINFO5\t 74 23 03 92 00 00 00 EC 02 10 00 E2 00 77\t\x00\x00\x00\x00
\x01\f\x01\x00\x00\x009\xFEF\x06\x01\x06\x00\x03\x00\x03\xC6\x00\x02\xC6\x1F\x93\x17\x00
\xE2\a\f\x11\x1287\x03e\x01\x01\x00\x86\a\x91\x05\x94%\x96\x85\xF1\x87\x05\x16m\x915&\xAB
\x04\x03\x02\x06\xC0\xAD\x16\xA0\x140\x12\x06\t*\x86:\x00\x89a:\x01\x00\xA4\x050\x03\x81
\x01\a\xE1\x10\x02\x01\x01\x04\v\t\x01\n\n\x06\x02\x13i\x91gt\xE2#0\x03\xC2\x01\xF20\x03
\xC2\x01\xF10\x03\xC2\x01\xF60\x03\xC2\x01\xF50\x03\xC2\x01\xF40\x03\xC2\x01\xF30\x03\xC2
\x01\xF7\xB1\r\n\x01\x01\x04\b\n\x06\x02\x13i\x91gt\x00\x00*\x03\x00\x000000..."
I would like to extract the hexadecimal values between INFO5\t and \t..., so the output would be
"74 23 03 92 00 00 00 EC 02 10 00 E2 00 77"
I'm doing like below but only removes the first unwanted part and leaves \n\n\x06...000
How can I fix this?
irb(main)>: a.map(&:chr).join.gsub(/(\t .*\t )|(\t.*)/,"")
=> "74 23 03 92 00 00 00 EC 02 10 00 E2 00 77\n\n\x06\x02\x13i\x91gt\xE2#0
\x03\xC2\x01\xF20\x03\xC2\x01\xF10\x03\xC2\x01\xF60\x03\xC2\x01\xF50\x03\xC2
\x01\xF40\x03\xC2\x01\xF30\x03\xC2\x01\xF7\xB1\r\n\x01\x01\x04\b\n\x06\x02\
x13i\x91gt\x00\x00*\x03\x00\x0000000002"
Thanks for the help in advance.
UDPATE
Below attached sample binary file.
input.dat
Here are two approaches (a below is abbreviated from that given in the question).
a = [9, 32, 50, 53, 56, 53, 57, 9, 73, 78, 70, 79, 9, 73, 78, 70, 79, 53, 9,
32, 55, 52, 32, 50, 51, 32, 48, 51, 32, 57, 50, 32, 48, 48, 32, 48, 48,
32, 48, 48, 32, 69, 67, 32, 48, 50, 32, 49, 48, 32, 48, 48, 32, 69, 50,
32, 48, 48, 32, 55, 55, 9, 0, 0]
Extract from the string that had been unpacked to create a
str = a.pack("C*")
#=> "\t 25859\tINFO\tINFO5\t 74 23 03 92 00 00 00 EC 02 10 00 E2 00 77\t\x00\x00"
str[/(?<=INFO5\t).+?(?=\t)/].strip
#=> "74 23 03 92 00 00 00 EC 02 10 00 E2 00 77"
str is the string that had been converted to a (a = str.unpack("C*)), so it need not be computed.
(?<=INFO5\t ) and (?=\t) are respectively a positive lookbehind and a positive lookahead. They must be matched but are not part of the match that is returned. The ("non-greedy") question mark in .+? ensures that the match terminates immediately before the first tab is encountered. By contrast,
"abc\td\tef"[/(?<=a).+(?=\t)/]
#=> "bc\td"
Extract from a and convert to a string
pfix = "INFO5\t".unpack("C*")
#=> [73, 78, 70, 79, 53, 9]
pfix_size = pfix.size
#=> 6
sfix = [prefix.last]
#=> [9]
sfix_size = sfix.size
start = idx_start(a, pfix) + pfix_size
#=> 19
a[start..idx_start(a[start..-1], sfix) + start - 1].pack("C*").strip
#=> "74 23 03 92 00 00 00 EC 02 10 00 E2 00 77"
def idx_start(a, arr)
arr_size = arr.size
a.each_index.find { |i| a[i, arr_size] == arr }
end
I assume you mean a=str.unpack("C*") - you can unpack a string but not an array.
To get the result you want, you don't need to use unpack at all1 - just perform a regex:
str.match(/INFO5\t(.*?)\t/).to_a[1]
# => " 74 23 03 92 00 00 00 EC 02 10 00 E2 00 77"
Note that there's a leading space in the result, but you can adjust the regex according to your needs; I'm not going to try to guess the specification of this format.
Tips:
The ? in .*? is needed to make the * non-greedy.
The to_a avoids raiseing an error in case the match finds nothing.
EDIT
Your comment regarding "invalid byte sequence in UTF-8" indicates that your data is probably ASCII-8BIT (i.e. it's not compatible with UTF-8), but it's stored in a string whose encoding attribute is "UTF-8". It would help if you explain how you obtained that string, because the string's encoding appears to be wrong.
Solution 1 (this is ideal):
Read in the file as ASCII-8BIT:
str = File.read("input.dat", encoding: 'ASCII-8BIT')
Solution 2 (a workaround, if you can't control the input encoding):
# NOTE: this changes the encoding on `str`
str.force_encoding("ASCII-8BIT")
After you've done this, the .match should work.
Further Explanation
The reason your map(&:chr).join works is because .chr will produce either US-ASCII or ASCII-8BIT strings (the latter happens for bytes above 127), never UTF-8.
When you join those strings, your result is in ASCII-8BIT if any byte was above 127. So this is effectively the same as calling force_encoding("ASCII-8BIT"), except that map/join doesn't modify the original string's encoding like force_encoding does.
1unpack is unnecessary because a.map(&:chr).join is the same as arr.pack('C*') which gives you the original str. Even if you had to unpack the string for another purpose, I recommend using the original string instead of re-packing the array. Maybe you can encapsulate this into a data structure, e.g.:
i_data = InfoData.new(str)
i_data.bytes # array of bytes
i_data.hex_string # "74 23 03 ..."
Note that the above code won't work as-is - you need to write the InfoData class yourself.
I assume that you don't need the non-ascii bytes, so in first step I trim them to the first null byte using take_while
Then I convert ints to string using map(&:chr).join
Finally I match them using a regex that /INFO5\t ?([^\t]*)\t/ that assumes the interesting part is between INFO5\t and next \t
--
a=array.unpack("C*")
a.take_while{|e| e > 0}.map(&:chr).join.match(/INFO5\t ?([^\t]*)\t/)[1]
# => "74 23 03 92 00 00 00 EC 02 10 00 E2 00 77"

Store Ints & Char in global array

I'm trying an activity online and have come across a problem. I have data about molecules and am trying to build a molecular weight calculator. The data is formatted like this:
{1, 1.0079, "Hydrogen", "H"},
{2, 4.0026, "Helium", "He"},
{3, 6.941, "Lithium", "Li"}
where it has the the atomic number, the atomic weight, the name and the abbreviation.
I've used a struct:
struct element {
int atomicNumber;
double atomicWeight;
char elementName[25];
char abbriv[5];
};
and now I need to use a global array to actually store the information. I'm confused to as how I would do this as I have three different data types for each element (int, double, char). I've tried doing some research but can't find a problem similar to this. Is it possible to put this information into an array?
Also, I've only copied in 3 element descriptions above, in reality there is 109 in total so I'm having second thoughts on how to actually store large amounts of information.
The full list:
{1, 1.0079, "Hydrogen", "H"},
{2, 4.0026, "Helium", "He"},
{3, 6.941, "Lithium", "Li"},
{4, 9.0122, "Beryllium", "Be"},
{5, 10.811, "Boron", "B"},
{6, 12.0107, "Carbon", "C"},
{7, 14.0067, "Nitrogen", "N"},
{8, 15.9994, "Oxygen", "O"},
{9, 18.9984, "Fluorine", "F"},
{10, 20.1797, "Neon", "Ne"},
{11, 22.9897, "Sodium", "Na"},
{12, 24.305, "Magnesium", "Mg"},
{13, 26.9815, "Aluminum", "Al"},
{14, 28.0855, "Silicon", "Si"},
{15, 30.9738, "Phosphorus", "P"},
{16, 32.065, "Sulfur", "S"},
{17, 35.453, "Chlorine", "Cl"},
{18, 39.948, "Argon", "Ar"},
{19, 39.0983, "Potassium", "K"},
{20, 40.078, "Calcium", "Ca"},
{21, 44.9559, "Scandium", "Sc"},
{22, 47.867, "Titanium", "Ti"},
{23, 50.9415, "Vanadium", "V"},
{24, 51.9961, "Chromium", "Cr"},
{25, 54.938, "Manganese", "Mn"},
{26, 55.845, "Iron", "Fe"},
{27, 58.9332, "Cobalt", "Co"},
{28, 58.6934, "Nickel", "Ni"},
{29, 63.546, "Copper", "Cu"},
{30, 65.39, "Zinc", "Zn"},
{31, 69.723, "Gallium", "Ga"},
{32, 72.64, "Germanium", "Ge"},
{33, 74.9216, "Arsenic", "As"},
{34, 78.96, "Selenium", "Se"},
{35, 79.904, "Bromine", "Br"},
{36, 83.8, "Krypton", "Kr"},
{37, 85.4678, "Rubidium", "Rb"},
{38, 87.62, "Strontium", "Sr"},
{39, 88.9059, "Yttrium", "Y"},
{40, 91.224, "Zirconium", "Zr"},
{41, 92.9064, "Niobium", "Nb"},
{42, 95.94, "Molybdenum", "Mo"},
{43, 98, "Technetium", "Tc"},
{44, 101.07, "Ruthenium", "Ru"},
{45, 102.9055, "Rhodium", "Rh"},
{46, 106.42, "Palladium", "Pd"},
{47, 107.8682, "Silver", "Ag"},
{48, 112.411, "Cadmium", "Cd"},
{49, 114.818, "Indium", "In"},
{50, 118.71, "Tin", "Sn"},
{51, 121.76, "Antimony", "Sb"},
{52, 127.6, "Tellurium", "Te"},
{53, 126.9045, "Iodine", "I"},
{54, 131.293, "Xenon", "Xe"},
{55, 132.9055, "Cesium", "Cs"},
{56, 137.327, "Barium", "Ba"},
{57, 138.9055, "Lanthanum", "La"},
{58, 140.116, "Cerium", "Ce"},
{59, 140.9077, "Praseodymium", "Pr"},
{60, 144.24, "Neodymium", "Nd"},
{61, 145, "Promethium", "Pm"},
{62, 150.36, "Samarium", "Sm"},
{63, 151.964, "Europium", "Eu"},
{64, 157.25, "Gadolinium", "Gd"},
{65, 158.9253, "Terbium", "Tb"},
{66, 162.5, "Dysprosium", "Dy"},
{67, 164.9303, "Holmium", "Ho"},
{68, 167.259, "Erbium", "Er"},
{69, 168.9342, "Thulium", "Tm"},
{70, 173.04, "Ytterbium", "Yb"},
{71, 174.967, "Lutetium", "Lu"},
{72, 178.49, "Hafnium", "Hf"},
{73, 180.9479, "Tantalum", "Ta"},
{74, 183.84, "Tungsten", "W"},
{75, 186.207, "Rhenium", "Re"},
{76, 190.23, "Osmium", "Os"},
{77, 192.217, "Iridium", "Ir"},
{78, 195.078, "Platinum", "Pt"},
{79, 196.9665, "Gold", "Au"},
{80, 200.59, "Mercury", "Hg"},
{81, 204.3833, "Thallium", "Tl"},
{82, 207.2, "Lead", "Pb"},
{83, 208.9804, "Bismuth", "Bi"},
{84, 209, "Polonium", "Po"},
{85, 210, "Astatine", "At"},
{86, 222, "Radon", "Rn"},
{87, 223, "Francium", "Fr"},
{88, 226, "Radium", "Ra"},
{89, 227, "Actinium", "Ac"},
{90, 232.0381, "Thorium", "Th"},
{91, 231.0359, "Protactinium", "Pa"},
{92, 238.0289, "Uranium", "U"},
{93, 237, "Neptunium", "Np"},
{94, 244, "Plutonium", "Pu"},
{95, 243, "Americium", "Am"},
{96, 247, "Curium", "Cm"},
{97, 247, "Berkelium", "Bk"},
{98, 251, "Californium", "Cf"},
{99, 252, "Einsteinium", "Es"},
{100, 257, "Fermium", "Fm"},
{101, 258, "Mendelevium", "Md"},
{102, 259, "Nobelium", "No"},
{103, 262, "Lawrencium", "Lr"},
{104, 261, "Rutherfordium", "Rf"},
{105, 262, "Dubnium", "Db"},
{106, 266, "Seaborgium", "Sg"},
{107, 264, "Bohrium", "Bh"},
{108, 277, "Hassium", "Hs"},
{109, 268, "Meitnerium", "Mt"}
Yes you are on the right track, now you can create an array of struct variables and assign all those to it at once and access it via a loop.
Something like this:
#include<stdio.h>
#define NUM_OF_ELEMENTS 109
struct element {
int atomicNumber;
double atomicWeight;
char elementName[25];
char abbriv[5];
};
struct element elements[NUM_OF_ELEMENTS]={
{1, 1.0079, "Hydrogen", "H"},
{2, 4.0026, "Helium", "He"},
{3, 6.941, "Lithium", "Li"},
{4, 9.0122, "Beryllium", "Be"},
{5, 10.811, "Boron", "B"},
{6, 12.0107, "Carbon", "C"},
{7, 14.0067, "Nitrogen", "N"},
{8, 15.9994, "Oxygen", "O"},
{9, 18.9984, "Fluorine", "F"},
{10, 20.1797, "Neon", "Ne"},
{11, 22.9897, "Sodium", "Na"},
{12, 24.305, "Magnesium", "Mg"},
{13, 26.9815, "Aluminum", "Al"},
{14, 28.0855, "Silicon", "Si"},
{15, 30.9738, "Phosphorus", "P"},
{16, 32.065, "Sulfur", "S"},
{17, 35.453, "Chlorine", "Cl"},
{18, 39.948, "Argon", "Ar"},
{19, 39.0983, "Potassium", "K"},
{20, 40.078, "Calcium", "Ca"},
{21, 44.9559, "Scandium", "Sc"},
{22, 47.867, "Titanium", "Ti"},
{23, 50.9415, "Vanadium", "V"},
{24, 51.9961, "Chromium", "Cr"},
{25, 54.938, "Manganese", "Mn"},
{26, 55.845, "Iron", "Fe"},
{27, 58.9332, "Cobalt", "Co"},
{28, 58.6934, "Nickel", "Ni"},
{29, 63.546, "Copper", "Cu"},
{30, 65.39, "Zinc", "Zn"},
{31, 69.723, "Gallium", "Ga"},
{32, 72.64, "Germanium", "Ge"},
{33, 74.9216, "Arsenic", "As"},
{34, 78.96, "Selenium", "Se"},
{35, 79.904, "Bromine", "Br"},
{36, 83.8, "Krypton", "Kr"},
{37, 85.4678, "Rubidium", "Rb"},
{38, 87.62, "Strontium", "Sr"},
{39, 88.9059, "Yttrium", "Y"},
{40, 91.224, "Zirconium", "Zr"},
{41, 92.9064, "Niobium", "Nb"},
{42, 95.94, "Molybdenum", "Mo"},
{43, 98, "Technetium", "Tc"},
{44, 101.07, "Ruthenium", "Ru"},
{45, 102.9055, "Rhodium", "Rh"},
{46, 106.42, "Palladium", "Pd"},
{47, 107.8682, "Silver", "Ag"},
{48, 112.411, "Cadmium", "Cd"},
{49, 114.818, "Indium", "In"},
{50, 118.71, "Tin", "Sn"},
{51, 121.76, "Antimony", "Sb"},
{52, 127.6, "Tellurium", "Te"},
{53, 126.9045, "Iodine", "I"},
{54, 131.293, "Xenon", "Xe"},
{55, 132.9055, "Cesium", "Cs"},
{56, 137.327, "Barium", "Ba"},
{57, 138.9055, "Lanthanum", "La"},
{58, 140.116, "Cerium", "Ce"},
{59, 140.9077, "Praseodymium", "Pr"},
{60, 144.24, "Neodymium", "Nd"},
{61, 145, "Promethium", "Pm"},
{62, 150.36, "Samarium", "Sm"},
{63, 151.964, "Europium", "Eu"},
{64, 157.25, "Gadolinium", "Gd"},
{65, 158.9253, "Terbium", "Tb"},
{66, 162.5, "Dysprosium", "Dy"},
{67, 164.9303, "Holmium", "Ho"},
{68, 167.259, "Erbium", "Er"},
{69, 168.9342, "Thulium", "Tm"},
{70, 173.04, "Ytterbium", "Yb"},
{71, 174.967, "Lutetium", "Lu"},
{72, 178.49, "Hafnium", "Hf"},
{73, 180.9479, "Tantalum", "Ta"},
{74, 183.84, "Tungsten", "W"},
{75, 186.207, "Rhenium", "Re"},
{76, 190.23, "Osmium", "Os"},
{77, 192.217, "Iridium", "Ir"},
{78, 195.078, "Platinum", "Pt"},
{79, 196.9665, "Gold", "Au"},
{80, 200.59, "Mercury", "Hg"},
{81, 204.3833, "Thallium", "Tl"},
{82, 207.2, "Lead", "Pb"},
{83, 208.9804, "Bismuth", "Bi"},
{84, 209, "Polonium", "Po"},
{85, 210, "Astatine", "At"},
{86, 222, "Radon", "Rn"},
{87, 223, "Francium", "Fr"},
{88, 226, "Radium", "Ra"},
{89, 227, "Actinium", "Ac"},
{90, 232.0381, "Thorium", "Th"},
{91, 231.0359, "Protactinium", "Pa"},
{92, 238.0289, "Uranium", "U"},
{93, 237, "Neptunium", "Np"},
{94, 244, "Plutonium", "Pu"},
{95, 243, "Americium", "Am"},
{96, 247, "Curium", "Cm"},
{97, 247, "Berkelium", "Bk"},
{98, 251, "Californium", "Cf"},
{99, 252, "Einsteinium", "Es"},
{100, 257, "Fermium", "Fm"},
{101, 258, "Mendelevium", "Md"},
{102, 259, "Nobelium", "No"},
{103, 262, "Lawrencium", "Lr"},
{104, 261, "Rutherfordium", "Rf"},
{105, 262, "Dubnium", "Db"},
{106, 266, "Seaborgium", "Sg"},
{107, 264, "Bohrium", "Bh"},
{108, 277, "Hassium", "Hs"},
{109, 268, "Meitnerium", "Mt"}
};
void main()
{
int i;
printf("%13s\t%13s\t%25s\t%s\n", "Atomic Number", "Atomic Weight", "Element Name", "Abbrevation");
for(i = 0; i < NUM_OF_ELEMENTS; i++)
printf("%13d\t%13.2lf\t%25s\t%5s\n", elements[i].atomicNumber,
elements[i].atomicWeight,
elements[i].elementName,
elements[i].abbriv);
}
And here is the output:
$ gcc prgm.c
$ ./a.out
Atomic Number Atomic Weight Element Name Abbrevation
1 1.01 Hydrogen H
2 4.00 Helium He
3 6.94 Lithium Li
4 9.01 Beryllium Be
5 10.81 Boron B
6 12.01 Carbon C
7 14.01 Nitrogen N
8 16.00 Oxygen O
9 19.00 Fluorine F
10 20.18 Neon Ne
11 22.99 Sodium Na
12 24.30 Magnesium Mg
13 26.98 Aluminum Al
14 28.09 Silicon Si
15 30.97 Phosphorus P
16 32.06 Sulfur S
17 35.45 Chlorine Cl
18 39.95 Argon Ar
19 39.10 Potassium K
20 40.08 Calcium Ca
21 44.96 Scandium Sc
22 47.87 Titanium Ti
23 50.94 Vanadium V
24 52.00 Chromium Cr
25 54.94 Manganese Mn
26 55.84 Iron Fe
27 58.93 Cobalt Co
28 58.69 Nickel Ni
29 63.55 Copper Cu
30 65.39 Zinc Zn
31 69.72 Gallium Ga
32 72.64 Germanium Ge
33 74.92 Arsenic As
34 78.96 Selenium Se
35 79.90 Bromine Br
36 83.80 Krypton Kr
37 85.47 Rubidium Rb
38 87.62 Strontium Sr
39 88.91 Yttrium Y
40 91.22 Zirconium Zr
41 92.91 Niobium Nb
42 95.94 Molybdenum Mo
43 98.00 Technetium Tc
44 101.07 Ruthenium Ru
45 102.91 Rhodium Rh
46 106.42 Palladium Pd
47 107.87 Silver Ag
48 112.41 Cadmium Cd
49 114.82 Indium In
50 118.71 Tin Sn
51 121.76 Antimony Sb
52 127.60 Tellurium Te
53 126.90 Iodine I
54 131.29 Xenon Xe
55 132.91 Cesium Cs
56 137.33 Barium Ba
57 138.91 Lanthanum La
58 140.12 Cerium Ce
59 140.91 Praseodymium Pr
60 144.24 Neodymium Nd
61 145.00 Promethium Pm
62 150.36 Samarium Sm
63 151.96 Europium Eu
64 157.25 Gadolinium Gd
65 158.93 Terbium Tb
66 162.50 Dysprosium Dy
67 164.93 Holmium Ho
68 167.26 Erbium Er
69 168.93 Thulium Tm
70 173.04 Ytterbium Yb
71 174.97 Lutetium Lu
72 178.49 Hafnium Hf
73 180.95 Tantalum Ta
74 183.84 Tungsten W
75 186.21 Rhenium Re
76 190.23 Osmium Os
77 192.22 Iridium Ir
78 195.08 Platinum Pt
79 196.97 Gold Au
80 200.59 Mercury Hg
81 204.38 Thallium Tl
82 207.20 Lead Pb
83 208.98 Bismuth Bi
84 209.00 Polonium Po
85 210.00 Astatine At
86 222.00 Radon Rn
87 223.00 Francium Fr
88 226.00 Radium Ra
89 227.00 Actinium Ac
90 232.04 Thorium Th
91 231.04 Protactinium Pa
92 238.03 Uranium U
93 237.00 Neptunium Np
94 244.00 Plutonium Pu
95 243.00 Americium Am
96 247.00 Curium Cm
97 247.00 Berkelium Bk
98 251.00 Californium Cf
99 252.00 Einsteinium Es
100 257.00 Fermium Fm
101 258.00 Mendelevium Md
102 259.00 Nobelium No
103 262.00 Lawrencium Lr
104 261.00 Rutherfordium Rf
105 262.00 Dubnium Db
106 266.00 Seaborgium Sg
107 264.00 Bohrium Bh
108 277.00 Hassium Hs
109 268.00 Meitnerium Mt
$
What you're looking to do is creating an array of structs.
Eg.
struct elements myArray[108];
myArray[0].atomicNumber = 1;
myArray[0].atomicWeight = 1.0079;
myArray[0].elementName = "Hydrogen";
myArray[0].abbriv = "H";
Obviously there are a lot of elements in your table, so you can easily automate this process with a loop.

Using Grid-Like Data in C

I recently wrote code for a project euler problem, and by the time I had worked around every bug I ran into my code was pretty convoluted and no longer pretty and efficient. I had to manually manipulate my data far too much for my liking. I cannot find a straight forward answer elsewhere and would like a more graceful solution.
I'm not even sure this is possible in C, so keep that in mind.
The problem requires analyzing a grid of data that is in pain text.
The grid is as follows...
08 02 22 97 38 15 00 40 00 75 04 05 07 78 52 12 50 77 91 08
49 49 99 40 17 81 18 57 60 87 17 40 98 43 69 48 04 56 62 00
81 49 31 73 55 79 14 29 93 71 40 67 53 88 30 03 49 13 36 65
52 70 95 23 04 60 11 42 69 24 68 56 01 32 56 71 37 02 36 91
22 31 16 71 51 67 63 89 41 92 36 54 22 40 40 28 66 33 13 80
24 47 32 60 99 03 45 02 44 75 33 53 78 36 84 20 35 17 12 50
32 98 81 28 64 23 67 10 26 38 40 67 59 54 70 66 18 38 64 70
67 26 20 68 02 62 12 20 95 63 94 39 63 08 40 91 66 49 94 21
24 55 58 05 66 73 99 26 97 17 78 78 96 83 14 88 34 89 63 72
21 36 23 09 75 00 76 44 20 45 35 14 00 61 33 97 34 31 33 95
78 17 53 28 22 75 31 67 15 94 03 80 04 62 16 14 09 53 56 92
16 39 05 42 96 35 31 47 55 58 88 24 00 17 54 24 36 29 85 57
86 56 00 48 35 71 89 07 05 44 44 37 44 60 21 58 51 54 17 58
19 80 81 68 05 94 47 69 28 73 92 13 86 52 17 77 04 89 55 40
04 52 08 83 97 35 99 16 07 97 57 32 16 26 26 79 33 27 98 66
88 36 68 87 57 62 20 72 03 46 33 67 46 55 12 32 63 93 53 69
04 42 16 73 38 25 39 11 24 94 72 18 08 46 29 32 40 62 76 36
20 69 36 41 72 30 23 88 34 62 99 69 82 67 59 85 74 04 36 16
20 73 35 29 78 31 90 01 74 31 49 71 48 86 81 16 23 57 05 54
01 70 54 71 83 51 54 69 16 92 33 48 61 43 52 01 89 19 67 48
The idea is to find the largest possible product of four adjacent numbers (vertical, horizontal, or diagonal).
In the end my solution involved manually inputting this into a two-dimensional int array and manually changing all 08's or 09's to 8's and 9's to avoid the octal number problem.
Like so...
int str[20][20] = {{ 8, 02, 22, 97, 38, 15, 00, 40, 00, 75, 04, 05, 07, 78, 52, 12, 50, 77, 91, 8},{49, 49, 99, 40, 17, 81, 18, 57, 60, 87, 17, 40, 98, 43, 69, 48, 04, 56, 62, 00},{81, 49, 31, 73, 55, 79, 14, 29, 93, 71, 40, 67, 53, 88, 30, 03, 49, 13, 36, 65},{52, 70, 95, 23, 04, 60, 11, 42, 69, 24, 68, 56, 01, 32, 56, 71, 37, 02, 36, 91},{22, 31, 16, 71, 51, 67, 63, 89, 41, 92, 36, 54, 22, 40, 40, 28, 66, 33, 13, 80},{24, 47, 32, 60, 99, 03, 45, 02, 44, 75, 33, 53, 78, 36, 84, 20, 35, 17, 12, 50},{32, 98, 81, 28, 64, 23, 67, 10, 26, 38, 40, 67, 59, 54, 70, 66, 18, 38, 64, 70},{67, 26, 20, 68, 02, 62, 12, 20, 95, 63, 94, 39, 63, 8, 40, 91, 66, 49, 94, 21},{24, 55, 58, 05, 66, 73, 99, 26, 97, 17, 78, 78, 96, 83, 14, 88, 34, 89, 63, 72},{21, 36, 23, 9, 75, 00, 76, 44, 20, 45, 35, 14, 00, 61, 33, 97, 34, 31, 33, 95},{78, 17, 53, 28, 22, 75, 31, 67, 15, 94, 03, 80, 04, 62, 16, 14, 9, 53, 56, 92},{16, 39, 05, 42, 96, 35, 31, 47, 55, 58, 88, 24, 00, 17, 54, 24, 36, 29, 85, 57},{86, 56, 00, 48, 35, 71, 89, 07, 05, 44, 44, 37, 44, 60, 21, 58, 51, 54, 17, 58},{19, 80, 81, 68, 05, 94, 47, 69, 28, 73, 92, 13, 86, 52, 17, 77, 04, 89, 55, 40},{04, 52, 8, 83, 97, 35, 99, 16, 07, 97, 57, 32, 16, 26, 26, 79, 33, 27, 98, 66},{88, 36, 68, 87, 57, 62, 20, 72, 03, 46, 33, 67, 46, 55, 12, 32, 63, 93, 53, 69},{04, 42, 16, 73, 38, 25, 39, 11, 24, 94, 72, 18, 8, 46, 29, 32, 40, 62, 76, 36},{20, 69, 36, 41, 72, 30, 23, 88, 34, 62, 99, 69, 82, 67, 59, 85, 74, 04, 36, 16},{20, 73, 35, 29, 78, 31, 90, 01, 74, 31, 49, 71, 48, 86, 81, 16, 23, 57, 05, 54},{01, 70, 54, 71, 83, 51, 54, 69, 16, 92, 33, 48, 61, 43, 52, 01, 89, 19, 67, 48}};
This is not only tedious but it seems in efficient as well. Is there a way in c to take this data from the plain text grid, besides using a char string? And if not what would be a more elegant way to take this data?
I am self taught so I apologize for any glaring holes in what I know.
Is there a way in c to take this data from the plain text grid, besides using a char string? And if not what would be a more elegant way to take this data?
The approach to take is: save the data as a file (say input.txt) and pipe it to my program and read all of the entries through stdin. It would look like the following:
int rows = 20;
int cols = 20;
int arr[ rows ][ cols ] = { 0 };
int crow = 0;
int ccol = 0;
int num;
// Iterates until EOF is sent through stdin.
while ( scanf( "%d", &num ) != EOF ) {
// Determines whether we have filled all of the columns, if so
// reset the current column to 0 and increase the current row
// by 1.
if ( ccol >= 20 ) {
ccol = 0;
crow++;
}
// Mutate arr at position ( ( col * crow ) + ccol ) to have the
// value num.
arr[ crow ][ ccol ] = num;
}
... this would be inside a function in your driver file (possibly main). What this is doing is, reading each number one at a time then populating the array and stopping when EOF is sent (end of file). See documentation for scanf (here) for further details.
You would then run your program as follows to pipe the input file to your program:
./program.out < input.txt
Remark:
I am not using a dynamic array or blocks of memory from the memory pool. If you plan to receive an arbitrarily large file then I suggest implementing a dynamic array using the memory pool (as the stack is rather small in comparison to the memory pool).

Resources