To get the preferred width and height of a text object, you can use the properties m_TextComponent.preferredWidth and m_TextComponent.preferredHeight
You can also use the GetPreferredValues() functions.
There are several posts on the TextMesh Pro user forum about preferred values and these functions which a quick search would reveal.
Preferred values are based on the text metric whereas bounds are based on geometry. TextMesh Pro also include a .textBounds property which is based on text metrics.
You should also for testing purposes add the TMP_TextInfoDebugTool.cs to a text object as it will allow you to visualize all this information. This script is also good to learn how to access / use the information contained in the textInfo.
When working with all of this, you also have to be mindful that the text objects get processed late in the update cycle and just before the camera is rendered. As such changing the text in Awake(), Start(), Update(), etc… and then checking the bounds or any of these values before the text has been generated will results in the bounds, textInfo and all these data structures not having the correct information because the text hasn’t been processed / updated yet.
For when you need to get these data structure updated right away, you can use the .ForceMeshUpdate() function. There are several posts about this on the TMP user forum. Here is one such post http://digitalnativestudios.com/forum/index.php?topic=113.msg630#msg630
From that post
Since changes made to TextMesh Pro objects are processed once per frame (just before the rendering process takes place) their bounds don’t get updated until the objects (mesh) have been processed.
So in the following example, if you were to set the text via script and then read the bounds, these bounds would not be accurate because the mesh hasn’t been updated yet.
m_textMeshPro.text = "Some new text.";
Vector4 bounds = m_textMeshPro.bounds; // bounds will not reflect the "Some new text." because the mesh hasn't been updated yet.
However, if we force the mesh to be updated before we check the bounds again, then we will have the correct values.
m_textMeshPro.text = "Some new text.";
m_textMeshPro.ForceMeshUpdate(); // This forces the mesh to be updated now instead of just before the rendering process.
Vector4 bounds = m_textMeshPro.bounds; // Our bounds now correctly reflect this new text.